1use serde::de::{Deserialize, Deserializer};
2use serde::ser::{Serialize, Serializer};
3
4#[derive(Debug, Serialize, Eq, PartialEq, Hash)]
6pub enum ObjectType {
7 Agency,
9 Stop,
11 Route,
13 Trip,
15 Calendar,
17 Shape,
19 Fare,
21 Pathway,
23}
24
25#[derive(Debug, Default, Copy, Clone, PartialEq, Eq, Hash)]
27pub enum LocationType {
28 #[default]
30 StopPoint,
31 StopArea,
33 StationEntrance,
35 GenericNode,
37 BoardingArea,
39 Unknown(i16),
41}
42
43fn serialize_i16_as_str<S: Serializer>(s: S, value: i16) -> Result<S::Ok, S::Error> {
44 s.serialize_str(&value.to_string())
45}
46impl<'de> Deserialize<'de> for LocationType {
47 fn deserialize<D>(deserializer: D) -> Result<LocationType, D::Error>
48 where
49 D: Deserializer<'de>,
50 {
51 let s = <&str>::deserialize(deserializer)?;
52 Ok(match s {
53 "" | "0" => LocationType::StopPoint,
54 "1" => LocationType::StopArea,
55 "2" => LocationType::StationEntrance,
56 "3" => LocationType::GenericNode,
57 "4" => LocationType::BoardingArea,
58 s => LocationType::Unknown(s.parse().map_err(|_| {
59 serde::de::Error::custom(format!(
60 "invalid value for LocationType, must be an integer: {s}"
61 ))
62 })?),
63 })
64 }
65}
66
67impl Serialize for LocationType {
68 fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
69 where
70 S: Serializer,
71 {
72 serialize_i16_as_str(
74 serializer,
75 match self {
76 LocationType::StopPoint => 0,
77 LocationType::StopArea => 1,
78 LocationType::StationEntrance => 2,
79 LocationType::GenericNode => 3,
80 LocationType::BoardingArea => 4,
81 LocationType::Unknown(i) => *i,
82 },
83 )
84 }
85}
86
87#[derive(Debug, Clone, derive_more::TryFrom, Copy, PartialEq, Eq, Hash)]
88#[repr(i16)]
89#[try_from(repr)]
90pub enum ExtendedRouteType {
92 Railway = 100,
94 HighSpeedRail = 101,
96 LongDistanceTrains = 102,
98 InterRegionalRail = 103,
100 CarTransportRail = 104,
102 SleeperRail = 105,
104 RegionalRail = 106,
106 TouristRailway = 107,
108 RailShuttleWithinComplex = 108,
110 SuburbanRailway = 109,
112 ReplacementRail = 110,
114 SpecialRail = 111,
116 LorryTransportRail = 112,
118 OtherRail = 113,
120 CrossCountryRail = 114,
122 VehicleTransportRail = 115,
124 RackAndPinionRailway = 116,
126 AdditionalRail = 117,
128
129 Coach = 200,
131 InternationalCoach = 201,
133 NationalCoach = 202,
135 ShuttleCoach = 203,
137 RegionalCoach = 204,
139 SpecialCoach = 205,
141 SightseeingCoach = 206,
143 TouristCoach = 207,
145 CommuterCoach = 208,
147 OtherCoach = 209,
149
150 UrbanRailway = 400,
152 Metro = 401,
154 Underground = 402,
156 UrbanRailwayServiceDetail = 403,
158 OtherUrbanRailway = 404,
160 Monorail = 405,
162
163 Bus = 700,
165 RegionalBus = 701,
167 ExpressBus = 702,
169 StoppingBus = 703,
171 LocalBus = 704,
173 NightBus = 705,
175 PostBus = 706,
177 SpecialNeedsBus = 707,
179 MobilityBus = 708,
181 MobilityBusForRegisteredDisabled = 709,
183 SightseeingBus = 710,
185 ShuttleBus = 711,
187 SchoolBus = 712,
189 SchoolAndPublicServiceBus = 713,
191 RailReplacementBus = 714,
193 DemandAndResponseBus = 715,
195 OtherBus = 716,
197
198 Trolleybus = 800,
200
201 Tram = 900,
203 CityTram = 901,
205 LocalTram = 902,
207 RegionalTram = 903,
209 SightseeingTram = 904,
211 ShuttleTram = 905,
213 OtherTram = 906,
215
216 WaterTransport = 1000,
218 Air = 1100,
220 Ferry = 1200,
222
223 AerialLift = 1300,
225 Telecabin = 1301,
227 CableCar = 1302,
229 Elevator = 1303,
231 ChairLift = 1304,
233 DragLift = 1305,
235 SmallTelecabin = 1306,
237 OtherTelecabin = 1307,
239
240 Funicular = 1400,
243
244 Taxi = 1500,
246 CommunalTaxi = 1501,
248 WaterTaxi = 1502,
250 RailTaxi = 1503,
252 BikeTaxi = 1504,
254 LicensedTaxi = 1505,
256 PrivateHireServiceVehicle = 1506,
258 OtherTaxi = 1507,
260
261 MiscellaneousService = 1700,
263 HorseDrawnCarriage = 1702,
265}
266
267#[derive(Debug, Default, Copy, Clone, PartialEq, Eq, Hash)]
271pub enum RouteType {
272 Tramway,
274 Subway,
276 Rail,
278 #[default]
280 Bus,
281 Ferry,
283 CableCar,
285 Gondola,
287 Funicular,
289 Extended(ExtendedRouteType),
291 Other(i16),
293}
294
295impl ExtendedRouteType {
296 pub fn to_standard_route_type(&self) -> RouteType {
299 let int = *self as i16;
300 let hundreds = int / 100;
301 match hundreds {
302 1 => RouteType::Rail,
303 4 => RouteType::Subway,
304 2 | 7 | 8 => RouteType::Bus,
305 9 => RouteType::Tramway,
306 10 | 12 => RouteType::Ferry,
307 13 => RouteType::Gondola,
308 14 => RouteType::Funicular,
309 _ => RouteType::Extended(*self),
310 }
311 }
312}
313
314impl<'de> Deserialize<'de> for RouteType {
315 fn deserialize<D>(deserializer: D) -> Result<RouteType, D::Error>
316 where
317 D: Deserializer<'de>,
318 {
319 let i = i16::deserialize(deserializer)?;
320 if let Ok(ert) = ExtendedRouteType::try_from(i) {
321 return Ok(RouteType::Extended(ert));
322 }
323
324 Ok(match i {
325 0 => RouteType::Tramway,
326 1 => RouteType::Subway,
327 2 => RouteType::Rail,
328 3 => RouteType::Bus,
329 4 => RouteType::Ferry,
330 5 => RouteType::CableCar,
331 6 => RouteType::Gondola,
332 7 => RouteType::Funicular,
333 _ => RouteType::Other(i),
334 })
335 }
336}
337
338impl Serialize for RouteType {
339 fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
340 where
341 S: Serializer,
342 {
343 serializer.serialize_i16(match self {
344 RouteType::Tramway => 0,
345 RouteType::Subway => 1,
346 RouteType::Rail => 2,
347 RouteType::Bus => 3,
348 RouteType::Ferry => 4,
349 RouteType::CableCar => 5,
350 RouteType::Gondola => 6,
351 RouteType::Funicular => 7,
352 RouteType::Extended(ert) => *ert as i16,
353 RouteType::Other(i) => *i,
354 })
355 }
356}
357
358#[derive(Debug, Default, Copy, Clone, PartialEq, Eq, Hash)]
360pub enum PickupDropOffType {
361 #[default]
363 Regular,
364 NotAvailable,
366 ArrangeByPhone,
368 CoordinateWithDriver,
370 Unknown(i16),
372}
373
374impl<'de> Deserialize<'de> for PickupDropOffType {
375 fn deserialize<D>(deserializer: D) -> Result<PickupDropOffType, D::Error>
376 where
377 D: Deserializer<'de>,
378 {
379 let s = <&str>::deserialize(deserializer)?;
380 Ok(match s {
381 "" | "0" => PickupDropOffType::Regular,
382 "1" => PickupDropOffType::NotAvailable,
383 "2" => PickupDropOffType::ArrangeByPhone,
384 "3" => PickupDropOffType::CoordinateWithDriver,
385 s => PickupDropOffType::Unknown(s.parse().map_err(|_| {
386 serde::de::Error::custom(format!(
387 "invalid value for PickupDropOffType, must be an integer: {s}"
388 ))
389 })?),
390 })
391 }
392}
393
394impl Serialize for PickupDropOffType {
395 fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
396 where
397 S: Serializer,
398 {
399 serialize_i16_as_str(
401 serializer,
402 match self {
403 PickupDropOffType::Regular => 0,
404 PickupDropOffType::NotAvailable => 1,
405 PickupDropOffType::ArrangeByPhone => 2,
406 PickupDropOffType::CoordinateWithDriver => 3,
407 PickupDropOffType::Unknown(i) => *i,
408 },
409 )
410 }
411}
412
413#[derive(Debug, Default, Copy, Clone, PartialEq, Eq, Hash)]
417pub enum ContinuousPickupDropOff {
418 Continuous,
420 #[default]
422 NotAvailable,
423 ArrangeByPhone,
425 CoordinateWithDriver,
427 Unknown(i16),
429}
430
431impl Serialize for ContinuousPickupDropOff {
432 fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
433 where
434 S: Serializer,
435 {
436 serialize_i16_as_str(
438 serializer,
439 match self {
440 ContinuousPickupDropOff::Continuous => 0,
441 ContinuousPickupDropOff::NotAvailable => 1,
442 ContinuousPickupDropOff::ArrangeByPhone => 2,
443 ContinuousPickupDropOff::CoordinateWithDriver => 3,
444 ContinuousPickupDropOff::Unknown(i) => *i,
445 },
446 )
447 }
448}
449
450impl<'de> Deserialize<'de> for ContinuousPickupDropOff {
451 fn deserialize<D>(deserializer: D) -> Result<ContinuousPickupDropOff, D::Error>
452 where
453 D: Deserializer<'de>,
454 {
455 let s = <&str>::deserialize(deserializer)?;
456 Ok(match s {
457 "0" => ContinuousPickupDropOff::Continuous,
458 "" | "1" => ContinuousPickupDropOff::NotAvailable,
459 "2" => ContinuousPickupDropOff::ArrangeByPhone,
460 "3" => ContinuousPickupDropOff::CoordinateWithDriver,
461 s => ContinuousPickupDropOff::Unknown(s.parse().map_err(|_| {
462 serde::de::Error::custom(format!(
463 "invalid value for ContinuousPickupDropOff, must be an integer: {s}"
464 ))
465 })?),
466 })
467 }
468}
469
470#[derive(Debug, Default, Serialize, Copy, Clone, PartialEq, Eq, Hash)]
472pub enum TimepointType {
473 #[serde(rename = "0")]
475 Approximate = 0,
476 #[default]
478 #[serde(rename = "1")]
479 Exact = 1,
480}
481
482impl<'de> Deserialize<'de> for TimepointType {
483 fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
484 where
485 D: Deserializer<'de>,
486 {
487 let s = <&str>::deserialize(deserializer)?;
488 match s {
489 "" | "1" => Ok(Self::Exact),
490 "0" => Ok(Self::Approximate),
491 v => Err(serde::de::Error::custom(format!(
492 "invalid value for timepoint: {v}"
493 ))),
494 }
495 }
496}
497
498#[derive(Debug, Default, PartialEq, Eq, Hash, Clone, Copy)]
500pub enum Availability {
501 #[default]
503 InformationNotAvailable,
504 Available,
506 NotAvailable,
508 Unknown(i16),
510}
511
512impl<'de> Deserialize<'de> for Availability {
513 fn deserialize<D>(deserializer: D) -> Result<Availability, D::Error>
514 where
515 D: Deserializer<'de>,
516 {
517 let s = <&str>::deserialize(deserializer)?;
518 Ok(match s {
519 "" | "0" => Availability::InformationNotAvailable,
520 "1" => Availability::Available,
521 "2" => Availability::NotAvailable,
522 s => Availability::Unknown(s.parse().map_err(|_| {
523 serde::de::Error::custom(format!(
524 "invalid value for Availability, must be an integer: {s}"
525 ))
526 })?),
527 })
528 }
529}
530
531impl Serialize for Availability {
532 fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
533 where
534 S: Serializer,
535 {
536 serialize_i16_as_str(
538 serializer,
539 match self {
540 Availability::InformationNotAvailable => 0,
541 Availability::Available => 1,
542 Availability::NotAvailable => 2,
543 Availability::Unknown(i) => *i,
544 },
545 )
546 }
547}
548
549#[derive(Serialize, Deserialize, Debug, PartialEq, Eq, Hash, Clone, Copy)]
551pub enum Exception {
552 #[serde(rename = "1")]
554 Added,
555 #[serde(rename = "2")]
557 Deleted,
558}
559
560#[derive(Debug, Deserialize, Serialize, Copy, Clone, PartialEq, Eq, Hash)]
562pub enum DirectionType {
563 #[serde(rename = "0")]
565 Outbound,
566 #[serde(rename = "1")]
568 Inbound,
569}
570
571#[derive(Debug, Default, Copy, Clone, PartialEq, Eq, Hash)]
573pub enum BikesAllowedType {
574 #[default]
576 NoBikeInfo,
577 AtLeastOneBike,
579 NoBikesAllowed,
581 Unknown(i16),
583}
584
585impl<'de> Deserialize<'de> for BikesAllowedType {
586 fn deserialize<D>(deserializer: D) -> Result<BikesAllowedType, D::Error>
587 where
588 D: Deserializer<'de>,
589 {
590 let s = <&str>::deserialize(deserializer)?;
591 Ok(match s {
592 "" | "0" => BikesAllowedType::NoBikeInfo,
593 "1" => BikesAllowedType::AtLeastOneBike,
594 "2" => BikesAllowedType::NoBikesAllowed,
595 s => BikesAllowedType::Unknown(s.parse().map_err(|_| {
596 serde::de::Error::custom(format!(
597 "invalid value for BikeAllowedType, must be an integer: {s}"
598 ))
599 })?),
600 })
601 }
602}
603
604impl Serialize for BikesAllowedType {
605 fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
606 where
607 S: Serializer,
608 {
609 serialize_i16_as_str(
611 serializer,
612 match self {
613 BikesAllowedType::NoBikeInfo => 0,
614 BikesAllowedType::AtLeastOneBike => 1,
615 BikesAllowedType::NoBikesAllowed => 2,
616 BikesAllowedType::Unknown(i) => *i,
617 },
618 )
619 }
620}
621
622#[derive(Debug, Default, Copy, Clone, PartialEq, Eq, Hash)]
624pub enum CarsAllowedType {
625 #[default]
627 NoCarInfo,
628 AtLeastOneCar,
630 NoCarsAllowed,
632 Unknown(i16),
634}
635
636impl<'de> Deserialize<'de> for CarsAllowedType {
637 fn deserialize<D>(deserializer: D) -> Result<CarsAllowedType, D::Error>
638 where
639 D: Deserializer<'de>,
640 {
641 let s = <&str>::deserialize(deserializer)?;
642 Ok(match s {
643 "" | "0" => CarsAllowedType::NoCarInfo,
644 "1" => CarsAllowedType::AtLeastOneCar,
645 "2" => CarsAllowedType::NoCarsAllowed,
646 s => CarsAllowedType::Unknown(s.parse().map_err(|_| {
647 serde::de::Error::custom(format!(
648 "invalid value for CarsAllowedType, must be an integer: {s}"
649 ))
650 })?),
651 })
652 }
653}
654
655impl Serialize for CarsAllowedType {
656 fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
657 where
658 S: Serializer,
659 {
660 serialize_i16_as_str(
662 serializer,
663 match self {
664 CarsAllowedType::NoCarInfo => 0,
665 CarsAllowedType::AtLeastOneCar => 1,
666 CarsAllowedType::NoCarsAllowed => 2,
667 CarsAllowedType::Unknown(i) => *i,
668 },
669 )
670 }
671}
672#[derive(Debug, Deserialize, Serialize, Copy, Clone, PartialEq, Eq)]
674pub enum PaymentMethod {
675 #[serde(rename = "0")]
677 Aboard,
678 #[serde(rename = "1")]
680 PreBoarding,
681}
682
683#[derive(Debug, Serialize, Copy, Clone, PartialEq, Eq, Hash)]
685pub enum ExactTimes {
686 FrequencyBased = 0,
688 ScheduleBased = 1,
690}
691
692impl<'de> Deserialize<'de> for ExactTimes {
693 fn deserialize<D>(deserializer: D) -> Result<ExactTimes, D::Error>
694 where
695 D: Deserializer<'de>,
696 {
697 let s = <&str>::deserialize(deserializer)?;
698 Ok(match s {
699 "" | "0" => ExactTimes::FrequencyBased,
700 "1" => ExactTimes::ScheduleBased,
701 &_ => {
702 return Err(serde::de::Error::custom(format!(
703 "Invalid value `{s}`, expected 0 or 1"
704 )));
705 }
706 })
707 }
708}
709
710#[derive(Debug, Default, Copy, Clone, PartialEq, Eq, Hash)]
712pub enum Transfers {
713 #[default]
715 Unlimited,
716 NoTransfer,
718 UniqueTransfer,
720 TwoTransfers,
722 Other(i16),
724}
725
726impl<'de> Deserialize<'de> for Transfers {
727 fn deserialize<D>(deserializer: D) -> Result<Transfers, D::Error>
728 where
729 D: Deserializer<'de>,
730 {
731 let i = Option::<i16>::deserialize(deserializer)?;
732 Ok(match i {
733 Some(0) => Transfers::NoTransfer,
734 Some(1) => Transfers::UniqueTransfer,
735 Some(2) => Transfers::TwoTransfers,
736 Some(a) => Transfers::Other(a),
737 None => Transfers::default(),
738 })
739 }
740}
741
742impl Serialize for Transfers {
743 fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
744 where
745 S: Serializer,
746 {
747 match self {
748 Transfers::NoTransfer => serialize_i16_as_str(serializer, 0),
749 Transfers::UniqueTransfer => serialize_i16_as_str(serializer, 1),
750 Transfers::TwoTransfers => serialize_i16_as_str(serializer, 2),
751 Transfers::Other(a) => serialize_i16_as_str(serializer, *a),
752 Transfers::Unlimited => serializer.serialize_none(),
753 }
754 }
755}
756#[derive(Debug, Serialize, Default, Copy, Clone, PartialEq, Eq, Hash)]
758pub enum TransferType {
759 #[serde(rename = "0")]
761 #[default]
762 Recommended,
763 #[serde(rename = "1")]
765 Timed,
766 #[serde(rename = "2")]
768 MinTime,
769 #[serde(rename = "3")]
771 Impossible,
772 #[serde(rename = "4")]
774 StayOnBoard,
775 #[serde(rename = "5")]
778 MustAlight,
779}
780
781impl<'de> Deserialize<'de> for TransferType {
782 fn deserialize<D>(deserializer: D) -> Result<TransferType, D::Error>
783 where
784 D: Deserializer<'de>,
785 {
786 let s = <&str>::deserialize(deserializer)?;
787 Ok(match s {
788 "" | "0" => TransferType::Recommended,
789 "1" => TransferType::Timed,
790 "2" => TransferType::MinTime,
791 "3" => TransferType::Impossible,
792 "4" => TransferType::StayOnBoard,
793 "5" => TransferType::MustAlight,
794 s => {
795 return Err(serde::de::Error::custom(format!(
796 "Invalid value `{s}`, expected 0, 1, 2, 3, 4, 5"
797 )));
798 }
799 })
800 }
801}
802
803#[derive(Debug, Serialize, Deserialize, Default, Copy, Clone, PartialEq, Eq, Hash)]
805pub enum PathwayMode {
806 #[serde(rename = "1")]
808 #[default]
809 Walkway,
810 #[serde(rename = "2")]
812 Stairs,
813 #[serde(rename = "3")]
815 MovingSidewalk,
816 #[serde(rename = "4")]
818 Escalator,
819 #[serde(rename = "5")]
821 Elevator,
822 #[serde(rename = "6")]
825 FareGate,
826 #[serde(rename = "7")]
829 ExitGate,
830}
831
832#[derive(Debug, Serialize, Deserialize, Default, Copy, Clone, PartialEq, Eq, Hash)]
834pub enum PathwayDirectionType {
835 #[serde(rename = "0")]
837 #[default]
838 Unidirectional,
839 #[serde(rename = "1")]
841 Bidirectional,
842}
843
844#[derive(Debug, Deserialize, Serialize, Copy, Clone, PartialEq, Eq)]
846pub enum FareMediaType {
847 #[serde(rename = "0")]
849 None,
850 #[serde(rename = "1")]
852 PhysicalPaperTicket,
853 #[serde(rename = "2")]
855 PhysicalTransitCard,
856 #[serde(rename = "3")]
858 CEmv,
859 #[serde(rename = "4")]
861 MobileApp,
862}
863
864#[derive(Debug, Serialize, Copy, Clone, PartialEq, Eq, Hash)]
866pub enum DefaultFareCategory {
867 NotDefault = 0,
869 Default = 1,
871}
872
873impl<'de> Deserialize<'de> for DefaultFareCategory {
874 fn deserialize<D>(deserializer: D) -> Result<DefaultFareCategory, D::Error>
875 where
876 D: Deserializer<'de>,
877 {
878 let s = <&str>::deserialize(deserializer)?;
879 Ok(match s {
880 "" | "0" => DefaultFareCategory::NotDefault,
881 "1" => DefaultFareCategory::Default,
882 &_ => {
883 return Err(serde::de::Error::custom(format!(
884 "Invalid value `{s}`, expected 0 or 1"
885 )));
886 }
887 })
888 }
889}
890
891#[derive(Debug, Default, Deserialize, Serialize, Copy, Clone, PartialEq, Eq)]
893pub enum TicketingType {
894 #[default]
896 #[serde(rename = "0")]
897 Available,
898 #[serde(rename = "1")]
900 Unavailable,
901}