1#![allow(dead_code)]
2
3use std::borrow::Cow;
4use std::fmt::{self, Display, Formatter};
5use std::ops::Deref;
6use std::sync::Arc;
7
8use crate::ext::ustr::UStr;
9use crate::types::Oid;
10
11pub(crate) use sqlx_core::type_info::TypeInfo;
12
13#[derive(Debug, Clone, PartialEq)]
43#[cfg_attr(feature = "offline", derive(serde::Serialize, serde::Deserialize))]
44pub struct PgTypeInfo(pub(crate) PgType);
45
46impl Deref for PgTypeInfo {
47 type Target = PgType;
48
49 fn deref(&self) -> &Self::Target {
50 &self.0
51 }
52}
53
54#[derive(Debug, Clone)]
55#[cfg_attr(feature = "offline", derive(serde::Serialize, serde::Deserialize))]
56#[repr(u32)]
57pub enum PgType {
58 Bool,
59 Bytea,
60 Char,
61 Name,
62 Int8,
63 Int2,
64 Int4,
65 Text,
66 Oid,
67 Json,
68 JsonArray,
69 Point,
70 Lseg,
71 Path,
72 Box,
73 Polygon,
74 Line,
75 LineArray,
76 Cidr,
77 CidrArray,
78 Float4,
79 Float8,
80 Unknown,
81 Circle,
82 CircleArray,
83 Macaddr8,
84 Macaddr8Array,
85 Macaddr,
86 Inet,
87 BoolArray,
88 ByteaArray,
89 CharArray,
90 NameArray,
91 Int2Array,
92 Int4Array,
93 TextArray,
94 BpcharArray,
95 VarcharArray,
96 Int8Array,
97 PointArray,
98 LsegArray,
99 PathArray,
100 BoxArray,
101 Float4Array,
102 Float8Array,
103 PolygonArray,
104 OidArray,
105 MacaddrArray,
106 InetArray,
107 Bpchar,
108 Varchar,
109 Date,
110 Time,
111 Timestamp,
112 TimestampArray,
113 DateArray,
114 TimeArray,
115 Timestamptz,
116 TimestamptzArray,
117 Interval,
118 IntervalArray,
119 NumericArray,
120 Timetz,
121 TimetzArray,
122 Bit,
123 BitArray,
124 Varbit,
125 VarbitArray,
126 Numeric,
127 Record,
128 RecordArray,
129 Uuid,
130 UuidArray,
131 Jsonb,
132 JsonbArray,
133 Int4Range,
134 Int4RangeArray,
135 NumRange,
136 NumRangeArray,
137 TsRange,
138 TsRangeArray,
139 TstzRange,
140 TstzRangeArray,
141 DateRange,
142 DateRangeArray,
143 Int8Range,
144 Int8RangeArray,
145 Jsonpath,
146 JsonpathArray,
147 Money,
148 MoneyArray,
149
150 Void,
152
153 Custom(Arc<PgCustomType>),
156
157 DeclareWithName(UStr),
159
160 DeclareWithOid(Oid),
163
164 DeclareArrayOf(Arc<PgArrayOf>),
165}
166
167#[derive(Debug, Clone)]
168#[cfg_attr(feature = "offline", derive(serde::Serialize, serde::Deserialize))]
169pub struct PgCustomType {
170 #[cfg_attr(feature = "offline", serde(skip))]
171 pub(crate) oid: Oid,
172 pub(crate) name: UStr,
173 pub(crate) kind: PgTypeKind,
174}
175
176#[derive(Debug, Clone)]
177#[cfg_attr(feature = "offline", derive(serde::Serialize, serde::Deserialize))]
178pub enum PgTypeKind {
179 Simple,
180 Pseudo,
181 Domain(PgTypeInfo),
182 Composite(Arc<[(String, PgTypeInfo)]>),
183 Array(PgTypeInfo),
184 Enum(Arc<[String]>),
185 Range(PgTypeInfo),
186}
187
188#[derive(Debug)]
189#[cfg_attr(feature = "offline", derive(serde::Serialize, serde::Deserialize))]
190pub struct PgArrayOf {
191 pub(crate) elem_name: UStr,
192 pub(crate) name: Box<str>,
193}
194
195impl PgTypeInfo {
196 pub(crate) fn try_from_oid(oid: Oid) -> Option<Self> {
198 PgType::try_from_oid(oid).map(Self)
199 }
200
201 pub fn kind(&self) -> &PgTypeKind {
203 self.0.kind()
204 }
205
206 pub fn oid(&self) -> Option<Oid> {
222 self.0.try_oid()
223 }
224
225 #[doc(hidden)]
226 pub fn __type_feature_gate(&self) -> Option<&'static str> {
227 if [
228 PgTypeInfo::DATE,
229 PgTypeInfo::TIME,
230 PgTypeInfo::TIMESTAMP,
231 PgTypeInfo::TIMESTAMPTZ,
232 PgTypeInfo::DATE_ARRAY,
233 PgTypeInfo::TIME_ARRAY,
234 PgTypeInfo::TIMESTAMP_ARRAY,
235 PgTypeInfo::TIMESTAMPTZ_ARRAY,
236 ]
237 .contains(self)
238 {
239 Some("time")
240 } else if [PgTypeInfo::UUID, PgTypeInfo::UUID_ARRAY].contains(self) {
241 Some("uuid")
242 } else if [
243 PgTypeInfo::JSON,
244 PgTypeInfo::JSONB,
245 PgTypeInfo::JSON_ARRAY,
246 PgTypeInfo::JSONB_ARRAY,
247 ]
248 .contains(self)
249 {
250 Some("json")
251 } else if [
252 PgTypeInfo::CIDR,
253 PgTypeInfo::INET,
254 PgTypeInfo::CIDR_ARRAY,
255 PgTypeInfo::INET_ARRAY,
256 ]
257 .contains(self)
258 {
259 Some("ipnetwork")
260 } else if [PgTypeInfo::MACADDR].contains(self) {
261 Some("mac_address")
262 } else if [PgTypeInfo::NUMERIC, PgTypeInfo::NUMERIC_ARRAY].contains(self) {
263 Some("bigdecimal")
264 } else {
265 None
266 }
267 }
268
269 pub const fn with_name(name: &'static str) -> Self {
311 Self(PgType::DeclareWithName(UStr::Static(name)))
312 }
313
314 pub fn array_of(elem_name: &'static str) -> Self {
319 Self(PgType::DeclareArrayOf(Arc::new(PgArrayOf {
321 elem_name: elem_name.into(),
322 name: format!("{elem_name}[]").into(),
323 })))
324 }
325
326 pub const fn with_oid(oid: Oid) -> Self {
337 Self(PgType::DeclareWithOid(oid))
338 }
339
340 pub fn type_eq(&self, other: &Self) -> bool {
344 self.eq_impl(other, false)
345 }
346}
347
348impl PgType {
355 pub(crate) fn try_from_oid(oid: Oid) -> Option<Self> {
357 Some(match oid.0 {
358 16 => PgType::Bool,
359 17 => PgType::Bytea,
360 18 => PgType::Char,
361 19 => PgType::Name,
362 20 => PgType::Int8,
363 21 => PgType::Int2,
364 23 => PgType::Int4,
365 25 => PgType::Text,
366 26 => PgType::Oid,
367 114 => PgType::Json,
368 199 => PgType::JsonArray,
369 600 => PgType::Point,
370 601 => PgType::Lseg,
371 602 => PgType::Path,
372 603 => PgType::Box,
373 604 => PgType::Polygon,
374 628 => PgType::Line,
375 629 => PgType::LineArray,
376 650 => PgType::Cidr,
377 651 => PgType::CidrArray,
378 700 => PgType::Float4,
379 701 => PgType::Float8,
380 705 => PgType::Unknown,
381 718 => PgType::Circle,
382 719 => PgType::CircleArray,
383 774 => PgType::Macaddr8,
384 775 => PgType::Macaddr8Array,
385 790 => PgType::Money,
386 791 => PgType::MoneyArray,
387 829 => PgType::Macaddr,
388 869 => PgType::Inet,
389 1000 => PgType::BoolArray,
390 1001 => PgType::ByteaArray,
391 1002 => PgType::CharArray,
392 1003 => PgType::NameArray,
393 1005 => PgType::Int2Array,
394 1007 => PgType::Int4Array,
395 1009 => PgType::TextArray,
396 1014 => PgType::BpcharArray,
397 1015 => PgType::VarcharArray,
398 1016 => PgType::Int8Array,
399 1017 => PgType::PointArray,
400 1018 => PgType::LsegArray,
401 1019 => PgType::PathArray,
402 1020 => PgType::BoxArray,
403 1021 => PgType::Float4Array,
404 1022 => PgType::Float8Array,
405 1027 => PgType::PolygonArray,
406 1028 => PgType::OidArray,
407 1040 => PgType::MacaddrArray,
408 1041 => PgType::InetArray,
409 1042 => PgType::Bpchar,
410 1043 => PgType::Varchar,
411 1082 => PgType::Date,
412 1083 => PgType::Time,
413 1114 => PgType::Timestamp,
414 1115 => PgType::TimestampArray,
415 1182 => PgType::DateArray,
416 1183 => PgType::TimeArray,
417 1184 => PgType::Timestamptz,
418 1185 => PgType::TimestamptzArray,
419 1186 => PgType::Interval,
420 1187 => PgType::IntervalArray,
421 1231 => PgType::NumericArray,
422 1266 => PgType::Timetz,
423 1270 => PgType::TimetzArray,
424 1560 => PgType::Bit,
425 1561 => PgType::BitArray,
426 1562 => PgType::Varbit,
427 1563 => PgType::VarbitArray,
428 1700 => PgType::Numeric,
429 2278 => PgType::Void,
430 2249 => PgType::Record,
431 2287 => PgType::RecordArray,
432 2950 => PgType::Uuid,
433 2951 => PgType::UuidArray,
434 3802 => PgType::Jsonb,
435 3807 => PgType::JsonbArray,
436 3904 => PgType::Int4Range,
437 3905 => PgType::Int4RangeArray,
438 3906 => PgType::NumRange,
439 3907 => PgType::NumRangeArray,
440 3908 => PgType::TsRange,
441 3909 => PgType::TsRangeArray,
442 3910 => PgType::TstzRange,
443 3911 => PgType::TstzRangeArray,
444 3912 => PgType::DateRange,
445 3913 => PgType::DateRangeArray,
446 3926 => PgType::Int8Range,
447 3927 => PgType::Int8RangeArray,
448 4072 => PgType::Jsonpath,
449 4073 => PgType::JsonpathArray,
450
451 _ => {
452 return None;
453 }
454 })
455 }
456
457 pub(crate) fn oid(&self) -> Oid {
458 match self.try_oid() {
459 Some(oid) => oid,
460 None => unreachable!("(bug) use of unresolved type declaration [oid]"),
461 }
462 }
463
464 pub(crate) fn try_oid(&self) -> Option<Oid> {
465 Some(match self {
466 PgType::Bool => Oid(16),
467 PgType::Bytea => Oid(17),
468 PgType::Char => Oid(18),
469 PgType::Name => Oid(19),
470 PgType::Int8 => Oid(20),
471 PgType::Int2 => Oid(21),
472 PgType::Int4 => Oid(23),
473 PgType::Text => Oid(25),
474 PgType::Oid => Oid(26),
475 PgType::Json => Oid(114),
476 PgType::JsonArray => Oid(199),
477 PgType::Point => Oid(600),
478 PgType::Lseg => Oid(601),
479 PgType::Path => Oid(602),
480 PgType::Box => Oid(603),
481 PgType::Polygon => Oid(604),
482 PgType::Line => Oid(628),
483 PgType::LineArray => Oid(629),
484 PgType::Cidr => Oid(650),
485 PgType::CidrArray => Oid(651),
486 PgType::Float4 => Oid(700),
487 PgType::Float8 => Oid(701),
488 PgType::Unknown => Oid(705),
489 PgType::Circle => Oid(718),
490 PgType::CircleArray => Oid(719),
491 PgType::Macaddr8 => Oid(774),
492 PgType::Macaddr8Array => Oid(775),
493 PgType::Money => Oid(790),
494 PgType::MoneyArray => Oid(791),
495 PgType::Macaddr => Oid(829),
496 PgType::Inet => Oid(869),
497 PgType::BoolArray => Oid(1000),
498 PgType::ByteaArray => Oid(1001),
499 PgType::CharArray => Oid(1002),
500 PgType::NameArray => Oid(1003),
501 PgType::Int2Array => Oid(1005),
502 PgType::Int4Array => Oid(1007),
503 PgType::TextArray => Oid(1009),
504 PgType::BpcharArray => Oid(1014),
505 PgType::VarcharArray => Oid(1015),
506 PgType::Int8Array => Oid(1016),
507 PgType::PointArray => Oid(1017),
508 PgType::LsegArray => Oid(1018),
509 PgType::PathArray => Oid(1019),
510 PgType::BoxArray => Oid(1020),
511 PgType::Float4Array => Oid(1021),
512 PgType::Float8Array => Oid(1022),
513 PgType::PolygonArray => Oid(1027),
514 PgType::OidArray => Oid(1028),
515 PgType::MacaddrArray => Oid(1040),
516 PgType::InetArray => Oid(1041),
517 PgType::Bpchar => Oid(1042),
518 PgType::Varchar => Oid(1043),
519 PgType::Date => Oid(1082),
520 PgType::Time => Oid(1083),
521 PgType::Timestamp => Oid(1114),
522 PgType::TimestampArray => Oid(1115),
523 PgType::DateArray => Oid(1182),
524 PgType::TimeArray => Oid(1183),
525 PgType::Timestamptz => Oid(1184),
526 PgType::TimestamptzArray => Oid(1185),
527 PgType::Interval => Oid(1186),
528 PgType::IntervalArray => Oid(1187),
529 PgType::NumericArray => Oid(1231),
530 PgType::Timetz => Oid(1266),
531 PgType::TimetzArray => Oid(1270),
532 PgType::Bit => Oid(1560),
533 PgType::BitArray => Oid(1561),
534 PgType::Varbit => Oid(1562),
535 PgType::VarbitArray => Oid(1563),
536 PgType::Numeric => Oid(1700),
537 PgType::Void => Oid(2278),
538 PgType::Record => Oid(2249),
539 PgType::RecordArray => Oid(2287),
540 PgType::Uuid => Oid(2950),
541 PgType::UuidArray => Oid(2951),
542 PgType::Jsonb => Oid(3802),
543 PgType::JsonbArray => Oid(3807),
544 PgType::Int4Range => Oid(3904),
545 PgType::Int4RangeArray => Oid(3905),
546 PgType::NumRange => Oid(3906),
547 PgType::NumRangeArray => Oid(3907),
548 PgType::TsRange => Oid(3908),
549 PgType::TsRangeArray => Oid(3909),
550 PgType::TstzRange => Oid(3910),
551 PgType::TstzRangeArray => Oid(3911),
552 PgType::DateRange => Oid(3912),
553 PgType::DateRangeArray => Oid(3913),
554 PgType::Int8Range => Oid(3926),
555 PgType::Int8RangeArray => Oid(3927),
556 PgType::Jsonpath => Oid(4072),
557 PgType::JsonpathArray => Oid(4073),
558
559 PgType::Custom(ty) => ty.oid,
560
561 PgType::DeclareWithOid(oid) => *oid,
562 PgType::DeclareWithName(_) => {
563 return None;
564 }
565 PgType::DeclareArrayOf(_) => {
566 return None;
567 }
568 })
569 }
570
571 pub(crate) fn display_name(&self) -> &str {
572 match self {
573 PgType::Bool => "BOOL",
574 PgType::Bytea => "BYTEA",
575 PgType::Char => "\"CHAR\"",
576 PgType::Name => "NAME",
577 PgType::Int8 => "INT8",
578 PgType::Int2 => "INT2",
579 PgType::Int4 => "INT4",
580 PgType::Text => "TEXT",
581 PgType::Oid => "OID",
582 PgType::Json => "JSON",
583 PgType::JsonArray => "JSON[]",
584 PgType::Point => "POINT",
585 PgType::Lseg => "LSEG",
586 PgType::Path => "PATH",
587 PgType::Box => "BOX",
588 PgType::Polygon => "POLYGON",
589 PgType::Line => "LINE",
590 PgType::LineArray => "LINE[]",
591 PgType::Cidr => "CIDR",
592 PgType::CidrArray => "CIDR[]",
593 PgType::Float4 => "FLOAT4",
594 PgType::Float8 => "FLOAT8",
595 PgType::Unknown => "UNKNOWN",
596 PgType::Circle => "CIRCLE",
597 PgType::CircleArray => "CIRCLE[]",
598 PgType::Macaddr8 => "MACADDR8",
599 PgType::Macaddr8Array => "MACADDR8[]",
600 PgType::Macaddr => "MACADDR",
601 PgType::Inet => "INET",
602 PgType::BoolArray => "BOOL[]",
603 PgType::ByteaArray => "BYTEA[]",
604 PgType::CharArray => "\"CHAR\"[]",
605 PgType::NameArray => "NAME[]",
606 PgType::Int2Array => "INT2[]",
607 PgType::Int4Array => "INT4[]",
608 PgType::TextArray => "TEXT[]",
609 PgType::BpcharArray => "CHAR[]",
610 PgType::VarcharArray => "VARCHAR[]",
611 PgType::Int8Array => "INT8[]",
612 PgType::PointArray => "POINT[]",
613 PgType::LsegArray => "LSEG[]",
614 PgType::PathArray => "PATH[]",
615 PgType::BoxArray => "BOX[]",
616 PgType::Float4Array => "FLOAT4[]",
617 PgType::Float8Array => "FLOAT8[]",
618 PgType::PolygonArray => "POLYGON[]",
619 PgType::OidArray => "OID[]",
620 PgType::MacaddrArray => "MACADDR[]",
621 PgType::InetArray => "INET[]",
622 PgType::Bpchar => "CHAR",
623 PgType::Varchar => "VARCHAR",
624 PgType::Date => "DATE",
625 PgType::Time => "TIME",
626 PgType::Timestamp => "TIMESTAMP",
627 PgType::TimestampArray => "TIMESTAMP[]",
628 PgType::DateArray => "DATE[]",
629 PgType::TimeArray => "TIME[]",
630 PgType::Timestamptz => "TIMESTAMPTZ",
631 PgType::TimestamptzArray => "TIMESTAMPTZ[]",
632 PgType::Interval => "INTERVAL",
633 PgType::IntervalArray => "INTERVAL[]",
634 PgType::NumericArray => "NUMERIC[]",
635 PgType::Timetz => "TIMETZ",
636 PgType::TimetzArray => "TIMETZ[]",
637 PgType::Bit => "BIT",
638 PgType::BitArray => "BIT[]",
639 PgType::Varbit => "VARBIT",
640 PgType::VarbitArray => "VARBIT[]",
641 PgType::Numeric => "NUMERIC",
642 PgType::Record => "RECORD",
643 PgType::RecordArray => "RECORD[]",
644 PgType::Uuid => "UUID",
645 PgType::UuidArray => "UUID[]",
646 PgType::Jsonb => "JSONB",
647 PgType::JsonbArray => "JSONB[]",
648 PgType::Int4Range => "INT4RANGE",
649 PgType::Int4RangeArray => "INT4RANGE[]",
650 PgType::NumRange => "NUMRANGE",
651 PgType::NumRangeArray => "NUMRANGE[]",
652 PgType::TsRange => "TSRANGE",
653 PgType::TsRangeArray => "TSRANGE[]",
654 PgType::TstzRange => "TSTZRANGE",
655 PgType::TstzRangeArray => "TSTZRANGE[]",
656 PgType::DateRange => "DATERANGE",
657 PgType::DateRangeArray => "DATERANGE[]",
658 PgType::Int8Range => "INT8RANGE",
659 PgType::Int8RangeArray => "INT8RANGE[]",
660 PgType::Jsonpath => "JSONPATH",
661 PgType::JsonpathArray => "JSONPATH[]",
662 PgType::Money => "MONEY",
663 PgType::MoneyArray => "MONEY[]",
664 PgType::Void => "VOID",
665 PgType::Custom(ty) => &ty.name,
666 PgType::DeclareWithOid(_) => "?",
667 PgType::DeclareWithName(name) => name,
668 PgType::DeclareArrayOf(array) => &array.name,
669 }
670 }
671
672 pub(crate) fn name(&self) -> &str {
673 match self {
674 PgType::Bool => "bool",
675 PgType::Bytea => "bytea",
676 PgType::Char => "char",
677 PgType::Name => "name",
678 PgType::Int8 => "int8",
679 PgType::Int2 => "int2",
680 PgType::Int4 => "int4",
681 PgType::Text => "text",
682 PgType::Oid => "oid",
683 PgType::Json => "json",
684 PgType::JsonArray => "_json",
685 PgType::Point => "point",
686 PgType::Lseg => "lseg",
687 PgType::Path => "path",
688 PgType::Box => "box",
689 PgType::Polygon => "polygon",
690 PgType::Line => "line",
691 PgType::LineArray => "_line",
692 PgType::Cidr => "cidr",
693 PgType::CidrArray => "_cidr",
694 PgType::Float4 => "float4",
695 PgType::Float8 => "float8",
696 PgType::Unknown => "unknown",
697 PgType::Circle => "circle",
698 PgType::CircleArray => "_circle",
699 PgType::Macaddr8 => "macaddr8",
700 PgType::Macaddr8Array => "_macaddr8",
701 PgType::Macaddr => "macaddr",
702 PgType::Inet => "inet",
703 PgType::BoolArray => "_bool",
704 PgType::ByteaArray => "_bytea",
705 PgType::CharArray => "_char",
706 PgType::NameArray => "_name",
707 PgType::Int2Array => "_int2",
708 PgType::Int4Array => "_int4",
709 PgType::TextArray => "_text",
710 PgType::BpcharArray => "_bpchar",
711 PgType::VarcharArray => "_varchar",
712 PgType::Int8Array => "_int8",
713 PgType::PointArray => "_point",
714 PgType::LsegArray => "_lseg",
715 PgType::PathArray => "_path",
716 PgType::BoxArray => "_box",
717 PgType::Float4Array => "_float4",
718 PgType::Float8Array => "_float8",
719 PgType::PolygonArray => "_polygon",
720 PgType::OidArray => "_oid",
721 PgType::MacaddrArray => "_macaddr",
722 PgType::InetArray => "_inet",
723 PgType::Bpchar => "bpchar",
724 PgType::Varchar => "varchar",
725 PgType::Date => "date",
726 PgType::Time => "time",
727 PgType::Timestamp => "timestamp",
728 PgType::TimestampArray => "_timestamp",
729 PgType::DateArray => "_date",
730 PgType::TimeArray => "_time",
731 PgType::Timestamptz => "timestamptz",
732 PgType::TimestamptzArray => "_timestamptz",
733 PgType::Interval => "interval",
734 PgType::IntervalArray => "_interval",
735 PgType::NumericArray => "_numeric",
736 PgType::Timetz => "timetz",
737 PgType::TimetzArray => "_timetz",
738 PgType::Bit => "bit",
739 PgType::BitArray => "_bit",
740 PgType::Varbit => "varbit",
741 PgType::VarbitArray => "_varbit",
742 PgType::Numeric => "numeric",
743 PgType::Record => "record",
744 PgType::RecordArray => "_record",
745 PgType::Uuid => "uuid",
746 PgType::UuidArray => "_uuid",
747 PgType::Jsonb => "jsonb",
748 PgType::JsonbArray => "_jsonb",
749 PgType::Int4Range => "int4range",
750 PgType::Int4RangeArray => "_int4range",
751 PgType::NumRange => "numrange",
752 PgType::NumRangeArray => "_numrange",
753 PgType::TsRange => "tsrange",
754 PgType::TsRangeArray => "_tsrange",
755 PgType::TstzRange => "tstzrange",
756 PgType::TstzRangeArray => "_tstzrange",
757 PgType::DateRange => "daterange",
758 PgType::DateRangeArray => "_daterange",
759 PgType::Int8Range => "int8range",
760 PgType::Int8RangeArray => "_int8range",
761 PgType::Jsonpath => "jsonpath",
762 PgType::JsonpathArray => "_jsonpath",
763 PgType::Money => "money",
764 PgType::MoneyArray => "_money",
765 PgType::Void => "void",
766 PgType::Custom(ty) => &ty.name,
767 PgType::DeclareWithOid(_) => "?",
768 PgType::DeclareWithName(name) => name,
769 PgType::DeclareArrayOf(array) => &array.name,
770 }
771 }
772
773 pub(crate) fn kind(&self) -> &PgTypeKind {
774 match self {
775 PgType::Bool => &PgTypeKind::Simple,
776 PgType::Bytea => &PgTypeKind::Simple,
777 PgType::Char => &PgTypeKind::Simple,
778 PgType::Name => &PgTypeKind::Simple,
779 PgType::Int8 => &PgTypeKind::Simple,
780 PgType::Int2 => &PgTypeKind::Simple,
781 PgType::Int4 => &PgTypeKind::Simple,
782 PgType::Text => &PgTypeKind::Simple,
783 PgType::Oid => &PgTypeKind::Simple,
784 PgType::Json => &PgTypeKind::Simple,
785 PgType::JsonArray => &PgTypeKind::Array(PgTypeInfo(PgType::Json)),
786 PgType::Point => &PgTypeKind::Simple,
787 PgType::Lseg => &PgTypeKind::Simple,
788 PgType::Path => &PgTypeKind::Simple,
789 PgType::Box => &PgTypeKind::Simple,
790 PgType::Polygon => &PgTypeKind::Simple,
791 PgType::Line => &PgTypeKind::Simple,
792 PgType::LineArray => &PgTypeKind::Array(PgTypeInfo(PgType::Line)),
793 PgType::Cidr => &PgTypeKind::Simple,
794 PgType::CidrArray => &PgTypeKind::Array(PgTypeInfo(PgType::Cidr)),
795 PgType::Float4 => &PgTypeKind::Simple,
796 PgType::Float8 => &PgTypeKind::Simple,
797 PgType::Unknown => &PgTypeKind::Simple,
798 PgType::Circle => &PgTypeKind::Simple,
799 PgType::CircleArray => &PgTypeKind::Array(PgTypeInfo(PgType::Circle)),
800 PgType::Macaddr8 => &PgTypeKind::Simple,
801 PgType::Macaddr8Array => &PgTypeKind::Array(PgTypeInfo(PgType::Macaddr8)),
802 PgType::Macaddr => &PgTypeKind::Simple,
803 PgType::Inet => &PgTypeKind::Simple,
804 PgType::BoolArray => &PgTypeKind::Array(PgTypeInfo(PgType::Bool)),
805 PgType::ByteaArray => &PgTypeKind::Array(PgTypeInfo(PgType::Bytea)),
806 PgType::CharArray => &PgTypeKind::Array(PgTypeInfo(PgType::Char)),
807 PgType::NameArray => &PgTypeKind::Array(PgTypeInfo(PgType::Name)),
808 PgType::Int2Array => &PgTypeKind::Array(PgTypeInfo(PgType::Int2)),
809 PgType::Int4Array => &PgTypeKind::Array(PgTypeInfo(PgType::Int4)),
810 PgType::TextArray => &PgTypeKind::Array(PgTypeInfo(PgType::Text)),
811 PgType::BpcharArray => &PgTypeKind::Array(PgTypeInfo(PgType::Bpchar)),
812 PgType::VarcharArray => &PgTypeKind::Array(PgTypeInfo(PgType::Varchar)),
813 PgType::Int8Array => &PgTypeKind::Array(PgTypeInfo(PgType::Int8)),
814 PgType::PointArray => &PgTypeKind::Array(PgTypeInfo(PgType::Point)),
815 PgType::LsegArray => &PgTypeKind::Array(PgTypeInfo(PgType::Lseg)),
816 PgType::PathArray => &PgTypeKind::Array(PgTypeInfo(PgType::Path)),
817 PgType::BoxArray => &PgTypeKind::Array(PgTypeInfo(PgType::Box)),
818 PgType::Float4Array => &PgTypeKind::Array(PgTypeInfo(PgType::Float4)),
819 PgType::Float8Array => &PgTypeKind::Array(PgTypeInfo(PgType::Float8)),
820 PgType::PolygonArray => &PgTypeKind::Array(PgTypeInfo(PgType::Polygon)),
821 PgType::OidArray => &PgTypeKind::Array(PgTypeInfo(PgType::Oid)),
822 PgType::MacaddrArray => &PgTypeKind::Array(PgTypeInfo(PgType::Macaddr)),
823 PgType::InetArray => &PgTypeKind::Array(PgTypeInfo(PgType::Inet)),
824 PgType::Bpchar => &PgTypeKind::Simple,
825 PgType::Varchar => &PgTypeKind::Simple,
826 PgType::Date => &PgTypeKind::Simple,
827 PgType::Time => &PgTypeKind::Simple,
828 PgType::Timestamp => &PgTypeKind::Simple,
829 PgType::TimestampArray => &PgTypeKind::Array(PgTypeInfo(PgType::Timestamp)),
830 PgType::DateArray => &PgTypeKind::Array(PgTypeInfo(PgType::Date)),
831 PgType::TimeArray => &PgTypeKind::Array(PgTypeInfo(PgType::Time)),
832 PgType::Timestamptz => &PgTypeKind::Simple,
833 PgType::TimestamptzArray => &PgTypeKind::Array(PgTypeInfo(PgType::Timestamptz)),
834 PgType::Interval => &PgTypeKind::Simple,
835 PgType::IntervalArray => &PgTypeKind::Array(PgTypeInfo(PgType::Interval)),
836 PgType::NumericArray => &PgTypeKind::Array(PgTypeInfo(PgType::Numeric)),
837 PgType::Timetz => &PgTypeKind::Simple,
838 PgType::TimetzArray => &PgTypeKind::Array(PgTypeInfo(PgType::Timetz)),
839 PgType::Bit => &PgTypeKind::Simple,
840 PgType::BitArray => &PgTypeKind::Array(PgTypeInfo(PgType::Bit)),
841 PgType::Varbit => &PgTypeKind::Simple,
842 PgType::VarbitArray => &PgTypeKind::Array(PgTypeInfo(PgType::Varbit)),
843 PgType::Numeric => &PgTypeKind::Simple,
844 PgType::Record => &PgTypeKind::Simple,
845 PgType::RecordArray => &PgTypeKind::Array(PgTypeInfo(PgType::Record)),
846 PgType::Uuid => &PgTypeKind::Simple,
847 PgType::UuidArray => &PgTypeKind::Array(PgTypeInfo(PgType::Uuid)),
848 PgType::Jsonb => &PgTypeKind::Simple,
849 PgType::JsonbArray => &PgTypeKind::Array(PgTypeInfo(PgType::Jsonb)),
850 PgType::Int4Range => &PgTypeKind::Range(PgTypeInfo::INT4),
851 PgType::Int4RangeArray => &PgTypeKind::Array(PgTypeInfo(PgType::Int4Range)),
852 PgType::NumRange => &PgTypeKind::Range(PgTypeInfo::NUMERIC),
853 PgType::NumRangeArray => &PgTypeKind::Array(PgTypeInfo(PgType::NumRange)),
854 PgType::TsRange => &PgTypeKind::Range(PgTypeInfo::TIMESTAMP),
855 PgType::TsRangeArray => &PgTypeKind::Array(PgTypeInfo(PgType::TsRange)),
856 PgType::TstzRange => &PgTypeKind::Range(PgTypeInfo::TIMESTAMPTZ),
857 PgType::TstzRangeArray => &PgTypeKind::Array(PgTypeInfo(PgType::TstzRange)),
858 PgType::DateRange => &PgTypeKind::Range(PgTypeInfo::DATE),
859 PgType::DateRangeArray => &PgTypeKind::Array(PgTypeInfo(PgType::DateRange)),
860 PgType::Int8Range => &PgTypeKind::Range(PgTypeInfo::INT8),
861 PgType::Int8RangeArray => &PgTypeKind::Array(PgTypeInfo(PgType::Int8Range)),
862 PgType::Jsonpath => &PgTypeKind::Simple,
863 PgType::JsonpathArray => &PgTypeKind::Array(PgTypeInfo(PgType::Jsonpath)),
864 PgType::Money => &PgTypeKind::Simple,
865 PgType::MoneyArray => &PgTypeKind::Array(PgTypeInfo(PgType::Money)),
866
867 PgType::Void => &PgTypeKind::Pseudo,
868
869 PgType::Custom(ty) => &ty.kind,
870
871 PgType::DeclareWithOid(oid) => {
872 unreachable!("(bug) use of unresolved type declaration [oid={}]", oid.0);
873 }
874 PgType::DeclareWithName(name) => {
875 unreachable!("(bug) use of unresolved type declaration [name={name}]");
876 }
877 PgType::DeclareArrayOf(array) => {
878 unreachable!(
879 "(bug) use of unresolved type declaration [array of={}]",
880 array.elem_name
881 );
882 }
883 }
884 }
885
886 pub(crate) fn try_array_element(&self) -> Option<Cow<'_, PgTypeInfo>> {
888 match self {
890 PgType::Bool => None,
891 PgType::BoolArray => Some(Cow::Owned(PgTypeInfo(PgType::Bool))),
892 PgType::Bytea => None,
893 PgType::ByteaArray => Some(Cow::Owned(PgTypeInfo(PgType::Bytea))),
894 PgType::Char => None,
895 PgType::CharArray => Some(Cow::Owned(PgTypeInfo(PgType::Char))),
896 PgType::Name => None,
897 PgType::NameArray => Some(Cow::Owned(PgTypeInfo(PgType::Name))),
898 PgType::Int8 => None,
899 PgType::Int8Array => Some(Cow::Owned(PgTypeInfo(PgType::Int8))),
900 PgType::Int2 => None,
901 PgType::Int2Array => Some(Cow::Owned(PgTypeInfo(PgType::Int2))),
902 PgType::Int4 => None,
903 PgType::Int4Array => Some(Cow::Owned(PgTypeInfo(PgType::Int4))),
904 PgType::Text => None,
905 PgType::TextArray => Some(Cow::Owned(PgTypeInfo(PgType::Text))),
906 PgType::Oid => None,
907 PgType::OidArray => Some(Cow::Owned(PgTypeInfo(PgType::Oid))),
908 PgType::Json => None,
909 PgType::JsonArray => Some(Cow::Owned(PgTypeInfo(PgType::Json))),
910 PgType::Point => None,
911 PgType::PointArray => Some(Cow::Owned(PgTypeInfo(PgType::Point))),
912 PgType::Lseg => None,
913 PgType::LsegArray => Some(Cow::Owned(PgTypeInfo(PgType::Lseg))),
914 PgType::Path => None,
915 PgType::PathArray => Some(Cow::Owned(PgTypeInfo(PgType::Path))),
916 PgType::Box => None,
917 PgType::BoxArray => Some(Cow::Owned(PgTypeInfo(PgType::Box))),
918 PgType::Polygon => None,
919 PgType::PolygonArray => Some(Cow::Owned(PgTypeInfo(PgType::Polygon))),
920 PgType::Line => None,
921 PgType::LineArray => Some(Cow::Owned(PgTypeInfo(PgType::Line))),
922 PgType::Cidr => None,
923 PgType::CidrArray => Some(Cow::Owned(PgTypeInfo(PgType::Cidr))),
924 PgType::Float4 => None,
925 PgType::Float4Array => Some(Cow::Owned(PgTypeInfo(PgType::Float4))),
926 PgType::Float8 => None,
927 PgType::Float8Array => Some(Cow::Owned(PgTypeInfo(PgType::Float8))),
928 PgType::Circle => None,
929 PgType::CircleArray => Some(Cow::Owned(PgTypeInfo(PgType::Circle))),
930 PgType::Macaddr8 => None,
931 PgType::Macaddr8Array => Some(Cow::Owned(PgTypeInfo(PgType::Macaddr8))),
932 PgType::Money => None,
933 PgType::MoneyArray => Some(Cow::Owned(PgTypeInfo(PgType::Money))),
934 PgType::Macaddr => None,
935 PgType::MacaddrArray => Some(Cow::Owned(PgTypeInfo(PgType::Macaddr))),
936 PgType::Inet => None,
937 PgType::InetArray => Some(Cow::Owned(PgTypeInfo(PgType::Inet))),
938 PgType::Bpchar => None,
939 PgType::BpcharArray => Some(Cow::Owned(PgTypeInfo(PgType::Bpchar))),
940 PgType::Varchar => None,
941 PgType::VarcharArray => Some(Cow::Owned(PgTypeInfo(PgType::Varchar))),
942 PgType::Date => None,
943 PgType::DateArray => Some(Cow::Owned(PgTypeInfo(PgType::Date))),
944 PgType::Time => None,
945 PgType::TimeArray => Some(Cow::Owned(PgTypeInfo(PgType::Time))),
946 PgType::Timestamp => None,
947 PgType::TimestampArray => Some(Cow::Owned(PgTypeInfo(PgType::Timestamp))),
948 PgType::Timestamptz => None,
949 PgType::TimestamptzArray => Some(Cow::Owned(PgTypeInfo(PgType::Timestamptz))),
950 PgType::Interval => None,
951 PgType::IntervalArray => Some(Cow::Owned(PgTypeInfo(PgType::Interval))),
952 PgType::Timetz => None,
953 PgType::TimetzArray => Some(Cow::Owned(PgTypeInfo(PgType::Timetz))),
954 PgType::Bit => None,
955 PgType::BitArray => Some(Cow::Owned(PgTypeInfo(PgType::Bit))),
956 PgType::Varbit => None,
957 PgType::VarbitArray => Some(Cow::Owned(PgTypeInfo(PgType::Varbit))),
958 PgType::Numeric => None,
959 PgType::NumericArray => Some(Cow::Owned(PgTypeInfo(PgType::Numeric))),
960 PgType::Record => None,
961 PgType::RecordArray => Some(Cow::Owned(PgTypeInfo(PgType::Record))),
962 PgType::Uuid => None,
963 PgType::UuidArray => Some(Cow::Owned(PgTypeInfo(PgType::Uuid))),
964 PgType::Jsonb => None,
965 PgType::JsonbArray => Some(Cow::Owned(PgTypeInfo(PgType::Jsonb))),
966 PgType::Int4Range => None,
967 PgType::Int4RangeArray => Some(Cow::Owned(PgTypeInfo(PgType::Int4Range))),
968 PgType::NumRange => None,
969 PgType::NumRangeArray => Some(Cow::Owned(PgTypeInfo(PgType::NumRange))),
970 PgType::TsRange => None,
971 PgType::TsRangeArray => Some(Cow::Owned(PgTypeInfo(PgType::TsRange))),
972 PgType::TstzRange => None,
973 PgType::TstzRangeArray => Some(Cow::Owned(PgTypeInfo(PgType::TstzRange))),
974 PgType::DateRange => None,
975 PgType::DateRangeArray => Some(Cow::Owned(PgTypeInfo(PgType::DateRange))),
976 PgType::Int8Range => None,
977 PgType::Int8RangeArray => Some(Cow::Owned(PgTypeInfo(PgType::Int8Range))),
978 PgType::Jsonpath => None,
979 PgType::JsonpathArray => Some(Cow::Owned(PgTypeInfo(PgType::Jsonpath))),
980 PgType::Unknown => None,
982 PgType::Void => None,
984
985 PgType::Custom(ty) => match &ty.kind {
986 PgTypeKind::Simple => None,
987 PgTypeKind::Pseudo => None,
988 PgTypeKind::Domain(_) => None,
989 PgTypeKind::Composite(_) => None,
990 PgTypeKind::Array(ref elem_type_info) => Some(Cow::Borrowed(elem_type_info)),
991 PgTypeKind::Enum(_) => None,
992 PgTypeKind::Range(_) => None,
993 },
994 PgType::DeclareWithOid(_) => None,
995 PgType::DeclareWithName(name) => {
996 UStr::strip_prefix(name, "_")
998 .map(|elem| Cow::Owned(PgTypeInfo(PgType::DeclareWithName(elem))))
999 }
1000 PgType::DeclareArrayOf(array) => Some(Cow::Owned(PgTypeInfo(PgType::DeclareWithName(
1001 array.elem_name.clone(),
1002 )))),
1003 }
1004 }
1005
1006 fn is_declare_with_oid(&self) -> bool {
1008 matches!(self, Self::DeclareWithOid(_))
1009 }
1010
1011 fn eq_impl(&self, other: &Self, soft_eq: bool) -> bool {
1016 if let (Some(a), Some(b)) = (self.try_oid(), other.try_oid()) {
1017 return a == b;
1019 }
1020
1021 if soft_eq && (self.is_declare_with_oid() || other.is_declare_with_oid()) {
1022 return true;
1028 }
1029
1030 if let (Some(elem_a), Some(elem_b)) = (self.try_array_element(), other.try_array_element())
1031 {
1032 return elem_a == elem_b;
1033 }
1034
1035 name_eq(self.name(), other.name())
1037 }
1038}
1039
1040impl TypeInfo for PgTypeInfo {
1041 fn name(&self) -> &str {
1042 self.0.display_name()
1043 }
1044
1045 fn is_null(&self) -> bool {
1046 false
1047 }
1048
1049 fn is_void(&self) -> bool {
1050 matches!(self.0, PgType::Void)
1051 }
1052
1053 fn type_compatible(&self, other: &Self) -> bool
1054 where
1055 Self: Sized,
1056 {
1057 self == other
1058 }
1059}
1060
1061impl PartialEq<PgCustomType> for PgCustomType {
1062 fn eq(&self, other: &PgCustomType) -> bool {
1063 other.oid == self.oid
1064 }
1065}
1066
1067impl PgTypeInfo {
1068 pub(crate) const BOOL: Self = Self(PgType::Bool);
1070 pub(crate) const BOOL_ARRAY: Self = Self(PgType::BoolArray);
1071
1072 pub(crate) const BYTEA: Self = Self(PgType::Bytea);
1074 pub(crate) const BYTEA_ARRAY: Self = Self(PgType::ByteaArray);
1075
1076 pub(crate) const UUID: Self = Self(PgType::Uuid);
1078 pub(crate) const UUID_ARRAY: Self = Self(PgType::UuidArray);
1079
1080 pub(crate) const RECORD: Self = Self(PgType::Record);
1082 pub(crate) const RECORD_ARRAY: Self = Self(PgType::RecordArray);
1083
1084 pub(crate) const JSON: Self = Self(PgType::Json);
1090 pub(crate) const JSON_ARRAY: Self = Self(PgType::JsonArray);
1091
1092 pub(crate) const JSONB: Self = Self(PgType::Jsonb);
1093 pub(crate) const JSONB_ARRAY: Self = Self(PgType::JsonbArray);
1094
1095 pub(crate) const JSONPATH: Self = Self(PgType::Jsonpath);
1096 pub(crate) const JSONPATH_ARRAY: Self = Self(PgType::JsonpathArray);
1097
1098 pub(crate) const CIDR: Self = Self(PgType::Cidr);
1104 pub(crate) const CIDR_ARRAY: Self = Self(PgType::CidrArray);
1105
1106 pub(crate) const INET: Self = Self(PgType::Inet);
1107 pub(crate) const INET_ARRAY: Self = Self(PgType::InetArray);
1108
1109 pub(crate) const MACADDR: Self = Self(PgType::Macaddr);
1110 pub(crate) const MACADDR_ARRAY: Self = Self(PgType::MacaddrArray);
1111
1112 pub(crate) const MACADDR8: Self = Self(PgType::Macaddr8);
1113 pub(crate) const MACADDR8_ARRAY: Self = Self(PgType::Macaddr8Array);
1114
1115 pub(crate) const NAME: Self = Self(PgType::Name);
1122 pub(crate) const NAME_ARRAY: Self = Self(PgType::NameArray);
1123
1124 pub(crate) const BPCHAR: Self = Self(PgType::Bpchar);
1126 pub(crate) const BPCHAR_ARRAY: Self = Self(PgType::BpcharArray);
1127
1128 pub(crate) const VARCHAR: Self = Self(PgType::Varchar);
1130 pub(crate) const VARCHAR_ARRAY: Self = Self(PgType::VarcharArray);
1131
1132 pub(crate) const TEXT: Self = Self(PgType::Text);
1134 pub(crate) const TEXT_ARRAY: Self = Self(PgType::TextArray);
1135
1136 pub(crate) const UNKNOWN: Self = Self(PgType::Unknown);
1138
1139 pub(crate) const CHAR: Self = Self(PgType::Char);
1146 pub(crate) const CHAR_ARRAY: Self = Self(PgType::CharArray);
1147
1148 pub(crate) const OID: Self = Self(PgType::Oid);
1150 pub(crate) const OID_ARRAY: Self = Self(PgType::OidArray);
1151
1152 pub(crate) const INT2: Self = Self(PgType::Int2);
1154 pub(crate) const INT2_ARRAY: Self = Self(PgType::Int2Array);
1155
1156 pub(crate) const INT4: Self = Self(PgType::Int4);
1158 pub(crate) const INT4_ARRAY: Self = Self(PgType::Int4Array);
1159
1160 pub(crate) const INT8: Self = Self(PgType::Int8);
1162 pub(crate) const INT8_ARRAY: Self = Self(PgType::Int8Array);
1163
1164 pub(crate) const FLOAT4: Self = Self(PgType::Float4);
1166 pub(crate) const FLOAT4_ARRAY: Self = Self(PgType::Float4Array);
1167
1168 pub(crate) const FLOAT8: Self = Self(PgType::Float8);
1170 pub(crate) const FLOAT8_ARRAY: Self = Self(PgType::Float8Array);
1171
1172 pub(crate) const NUMERIC: Self = Self(PgType::Numeric);
1174 pub(crate) const NUMERIC_ARRAY: Self = Self(PgType::NumericArray);
1175
1176 pub(crate) const MONEY: Self = Self(PgType::Money);
1178 pub(crate) const MONEY_ARRAY: Self = Self(PgType::MoneyArray);
1179
1180 pub(crate) const TIMESTAMP: Self = Self(PgType::Timestamp);
1187 pub(crate) const TIMESTAMP_ARRAY: Self = Self(PgType::TimestampArray);
1188
1189 pub(crate) const TIMESTAMPTZ: Self = Self(PgType::Timestamptz);
1191 pub(crate) const TIMESTAMPTZ_ARRAY: Self = Self(PgType::TimestamptzArray);
1192
1193 pub(crate) const DATE: Self = Self(PgType::Date);
1195 pub(crate) const DATE_ARRAY: Self = Self(PgType::DateArray);
1196
1197 pub(crate) const TIME: Self = Self(PgType::Time);
1199 pub(crate) const TIME_ARRAY: Self = Self(PgType::TimeArray);
1200
1201 pub(crate) const TIMETZ: Self = Self(PgType::Timetz);
1203 pub(crate) const TIMETZ_ARRAY: Self = Self(PgType::TimetzArray);
1204
1205 pub(crate) const INTERVAL: Self = Self(PgType::Interval);
1207 pub(crate) const INTERVAL_ARRAY: Self = Self(PgType::IntervalArray);
1208
1209 pub(crate) const POINT: Self = Self(PgType::Point);
1216 pub(crate) const POINT_ARRAY: Self = Self(PgType::PointArray);
1217
1218 pub(crate) const LINE: Self = Self(PgType::Line);
1220 pub(crate) const LINE_ARRAY: Self = Self(PgType::LineArray);
1221
1222 pub(crate) const LSEG: Self = Self(PgType::Lseg);
1224 pub(crate) const LSEG_ARRAY: Self = Self(PgType::LsegArray);
1225
1226 pub(crate) const BOX: Self = Self(PgType::Box);
1228 pub(crate) const BOX_ARRAY: Self = Self(PgType::BoxArray);
1229
1230 pub(crate) const PATH: Self = Self(PgType::Path);
1232 pub(crate) const PATH_ARRAY: Self = Self(PgType::PathArray);
1233
1234 pub(crate) const POLYGON: Self = Self(PgType::Polygon);
1236 pub(crate) const POLYGON_ARRAY: Self = Self(PgType::PolygonArray);
1237
1238 pub(crate) const CIRCLE: Self = Self(PgType::Circle);
1240 pub(crate) const CIRCLE_ARRAY: Self = Self(PgType::CircleArray);
1241
1242 pub(crate) const BIT: Self = Self(PgType::Bit);
1248 pub(crate) const BIT_ARRAY: Self = Self(PgType::BitArray);
1249
1250 pub(crate) const VARBIT: Self = Self(PgType::Varbit);
1251 pub(crate) const VARBIT_ARRAY: Self = Self(PgType::VarbitArray);
1252
1253 pub(crate) const INT4_RANGE: Self = Self(PgType::Int4Range);
1259 pub(crate) const INT4_RANGE_ARRAY: Self = Self(PgType::Int4RangeArray);
1260
1261 pub(crate) const NUM_RANGE: Self = Self(PgType::NumRange);
1262 pub(crate) const NUM_RANGE_ARRAY: Self = Self(PgType::NumRangeArray);
1263
1264 pub(crate) const TS_RANGE: Self = Self(PgType::TsRange);
1265 pub(crate) const TS_RANGE_ARRAY: Self = Self(PgType::TsRangeArray);
1266
1267 pub(crate) const TSTZ_RANGE: Self = Self(PgType::TstzRange);
1268 pub(crate) const TSTZ_RANGE_ARRAY: Self = Self(PgType::TstzRangeArray);
1269
1270 pub(crate) const DATE_RANGE: Self = Self(PgType::DateRange);
1271 pub(crate) const DATE_RANGE_ARRAY: Self = Self(PgType::DateRangeArray);
1272
1273 pub(crate) const INT8_RANGE: Self = Self(PgType::Int8Range);
1274 pub(crate) const INT8_RANGE_ARRAY: Self = Self(PgType::Int8RangeArray);
1275
1276 pub(crate) const VOID: Self = Self(PgType::Void);
1282}
1283
1284impl Display for PgTypeInfo {
1285 fn fmt(&self, f: &mut Formatter<'_>) -> fmt::Result {
1286 f.pad(self.name())
1287 }
1288}
1289
1290impl PartialEq<PgType> for PgType {
1291 fn eq(&self, other: &PgType) -> bool {
1292 self.eq_impl(other, true)
1293 }
1294}
1295
1296fn name_eq(name1: &str, name2: &str) -> bool {
1300 if name1.starts_with("U&") {
1302 return name1 == name2;
1304 }
1305
1306 let mut chars1 = identifier_chars(name1);
1307 let mut chars2 = identifier_chars(name2);
1308
1309 while let (Some(a), Some(b)) = (chars1.next(), chars2.next()) {
1310 if !a.eq(&b) {
1311 return false;
1312 }
1313 }
1314
1315 chars1.next().is_none() && chars2.next().is_none()
1316}
1317
1318struct IdentifierChar {
1319 ch: char,
1320 case_sensitive: bool,
1321}
1322
1323impl IdentifierChar {
1324 fn eq(&self, other: &Self) -> bool {
1325 if self.case_sensitive || other.case_sensitive {
1326 self.ch == other.ch
1327 } else {
1328 self.ch.eq_ignore_ascii_case(&other.ch)
1329 }
1330 }
1331}
1332
1333fn identifier_chars(ident: &str) -> impl Iterator<Item = IdentifierChar> + '_ {
1337 let mut case_sensitive = false;
1338 let mut last_char_quote = false;
1339
1340 ident.chars().filter_map(move |ch| {
1341 if ch == '"' {
1342 if last_char_quote {
1343 last_char_quote = false;
1344 } else {
1345 last_char_quote = true;
1346 return None;
1347 }
1348 } else if last_char_quote {
1349 last_char_quote = false;
1350 case_sensitive = !case_sensitive;
1351 }
1352
1353 Some(IdentifierChar { ch, case_sensitive })
1354 })
1355}
1356
1357#[test]
1358fn test_name_eq() {
1359 let test_values = [
1360 ("foo", "foo", true),
1361 ("foo", "Foo", true),
1362 ("foo", "FOO", true),
1363 ("foo", r#""foo""#, true),
1364 ("foo", r#""Foo""#, false),
1365 ("foo", "foo.foo", false),
1366 ("foo.foo", "foo.foo", true),
1367 ("foo.foo", "foo.Foo", true),
1368 ("foo.foo", "foo.FOO", true),
1369 ("foo.foo", "Foo.foo", true),
1370 ("foo.foo", "Foo.Foo", true),
1371 ("foo.foo", "FOO.FOO", true),
1372 ("foo.foo", "foo", false),
1373 ("foo.foo", r#"foo."foo""#, true),
1374 ("foo.foo", r#"foo."Foo""#, false),
1375 ("foo.foo", r#"foo."FOO""#, false),
1376 ];
1377
1378 for (left, right, eq) in test_values {
1379 assert_eq!(
1380 name_eq(left, right),
1381 eq,
1382 "failed check for name_eq({left:?}, {right:?})"
1383 );
1384 assert_eq!(
1385 name_eq(right, left),
1386 eq,
1387 "failed check for name_eq({right:?}, {left:?})"
1388 );
1389 }
1390}