use core::fmt::Write;
use icu_provider::{
prelude::icu_locale_core::subtags::{region, Region},
DataError, DataPayload, DataProvider,
};
use crate::{
provider::windows::{WindowsZonesToBcp47MapV1, WindowsZonesToBcp47MapV1Marker},
TimeZoneBcp47Id,
};
#[derive(Debug)]
pub struct WindowsTimeZoneMapper {
data: DataPayload<WindowsZonesToBcp47MapV1Marker>,
}
impl WindowsTimeZoneMapper {
#[allow(clippy::new_ret_no_self)]
#[cfg(feature = "compiled_data")]
pub fn new() -> WindowsTimeZoneMapperBorrowed<'static> {
WindowsTimeZoneMapperBorrowed::new()
}
icu_provider::gen_any_buffer_data_constructors!(() -> error: DataError,
functions: [
new: skip,
try_new_with_any_provider,
try_new_with_buffer_provider,
try_new_unstable,
Self,
]
);
#[doc = icu_provider::gen_any_buffer_unstable_docs!(UNSTABLE, Self::new)]
pub fn try_new_unstable<P>(provider: &P) -> Result<Self, DataError>
where
P: DataProvider<WindowsZonesToBcp47MapV1Marker> + ?Sized,
{
let data = provider.load(Default::default())?.payload;
Ok(Self { data })
}
pub fn as_borrowed(&self) -> WindowsTimeZoneMapperBorrowed {
WindowsTimeZoneMapperBorrowed {
data: self.data.get(),
}
}
}
#[derive(Debug)]
pub struct WindowsTimeZoneMapperBorrowed<'a> {
data: &'a WindowsZonesToBcp47MapV1<'a>,
}
#[cfg(feature = "compiled_data")]
impl Default for WindowsTimeZoneMapperBorrowed<'_> {
fn default() -> Self {
Self::new()
}
}
impl WindowsTimeZoneMapperBorrowed<'_> {
#[cfg(feature = "compiled_data")]
pub fn new() -> Self {
WindowsTimeZoneMapperBorrowed {
data: crate::provider::Baked::SINGLETON_WINDOWS_ZONES_TO_BCP47_MAP_V1_MARKER,
}
}
pub fn windows_tz_to_bcp47_id(
&self,
windows_tz: &str,
region: Option<Region>,
) -> Option<TimeZoneBcp47Id> {
let mut cursor = self.data.map.cursor();
cursor.write_str(windows_tz).ok()?;
cursor.step(b'/');
cursor
.write_str(region.unwrap_or(region!("001")).as_str())
.ok()?;
self.data.bcp47_ids.get(cursor.take_value()?)
}
}
#[cfg(test)]
mod tests {
use super::*;
use tinystr::tinystr;
#[test]
fn basic_windows_tz_lookup() {
let win_map = WindowsTimeZoneMapper::new();
let result = win_map.windows_tz_to_bcp47_id("Central Standard Time", None);
assert_eq!(result, Some(TimeZoneBcp47Id(tinystr!(8, "uschi"))));
let result = win_map.windows_tz_to_bcp47_id("Eastern Standard Time", None);
assert_eq!(result, Some(TimeZoneBcp47Id(tinystr!(8, "usnyc"))));
let result = win_map.windows_tz_to_bcp47_id("Eastern Standard Time", Some(region!("CA")));
assert_eq!(result, Some(TimeZoneBcp47Id(tinystr!(8, "cator"))));
let result = win_map.windows_tz_to_bcp47_id("GMT Standard Time", None);
assert_eq!(result, Some(TimeZoneBcp47Id(tinystr!(8, "gblon"))));
}
}