//! A trait that can be used to parse an item from an input.

use core::ops::Deref;

use num_conv::prelude::*;

use crate::error::TryFromParsed;
use crate::format_description::well_known::iso8601::EncodedConfig;
use crate::format_description::well_known::{Iso8601, Rfc2822, Rfc3339};
use crate::format_description::FormatItem;
#[cfg(feature = "alloc")]
use crate::format_description::OwnedFormatItem;
use crate::internal_macros::bug;
use crate::parsing::{Parsed, ParsedItem};
use crate::{error, Date, Month, OffsetDateTime, Time, UtcOffset, Weekday};

/// A type that can be parsed.
#[cfg_attr(__time_03_docs, doc(notable_trait))]
#[doc(alias = "Parseable")]
pub trait Parsable: sealed::Sealed {}
impl Parsable for FormatItem<'_> {}
impl Parsable for [FormatItem<'_>] {}
#[cfg(feature = "alloc")]
impl Parsable for OwnedFormatItem {}
#[cfg(feature = "alloc")]
impl Parsable for [OwnedFormatItem] {}
impl Parsable for Rfc2822 {}
impl Parsable for Rfc3339 {}
impl<const CONFIG: EncodedConfig> Parsable for Iso8601<CONFIG> {}
impl<T: Deref> Parsable for T where T::Target: Parsable {}

/// Seal the trait to prevent downstream users from implementing it, while still allowing it to
/// exist in generic bounds.
mod sealed {
    #[allow(clippy::wildcard_imports)]
    use super::*;
    use crate::{OffsetDateTime, PrimitiveDateTime};

    /// Parse the item using a format description and an input.
    pub trait Sealed {
        /// Parse the item into the provided [`Parsed`] struct.
        ///
        /// This method can be used to parse a single component without parsing the full value.
        fn parse_into<'a>(
            &self,
            input: &'a [u8],
            parsed: &mut Parsed,
        ) -> Result<&'a [u8], error::Parse>;

        /// Parse the item into a new [`Parsed`] struct.
        ///
        /// This method can only be used to parse a complete value of a type. If any characters
        /// remain after parsing, an error will be returned.
        fn parse(&self, input: &[u8]) -> Result<Parsed, error::Parse> {
            let mut parsed = Parsed::new();
            if self.parse_into(input, &mut parsed)?.is_empty() {
                Ok(parsed)
            } else {
                Err(error::Parse::ParseFromDescription(
                    error::ParseFromDescription::UnexpectedTrailingCharacters,
                ))
            }
        }

        /// Parse a [`Date`] from the format description.
        fn parse_date(&self, input: &[u8]) -> Result<Date, error::Parse> {
            Ok(self.parse(input)?.try_into()?)
        }

        /// Parse a [`Time`] from the format description.
        fn parse_time(&self, input: &[u8]) -> Result<Time, error::Parse> {
            Ok(self.parse(input)?.try_into()?)
        }

        /// Parse a [`UtcOffset`] from the format description.
        fn parse_offset(&self, input: &[u8]) -> Result<UtcOffset, error::Parse> {
            Ok(self.parse(input)?.try_into()?)
        }

        /// Parse a [`PrimitiveDateTime`] from the format description.
        fn parse_primitive_date_time(
            &self,
            input: &[u8],
        ) -> Result<PrimitiveDateTime, error::Parse> {
            Ok(self.parse(input)?.try_into()?)
        }

        /// Parse a [`OffsetDateTime`] from the format description.
        fn parse_offset_date_time(&self, input: &[u8]) -> Result<OffsetDateTime, error::Parse> {
            Ok(self.parse(input)?.try_into()?)
        }
    }
}

// region: custom formats
impl sealed::Sealed for FormatItem<'_> {
    fn parse_into<'a>(
        &self,
        input: &'a [u8],
        parsed: &mut Parsed,
    ) -> Result<&'a [u8], error::Parse> {
        Ok(parsed.parse_item(input, self)?)
    }
}

impl sealed::Sealed for [FormatItem<'_>] {
    fn parse_into<'a>(
        &self,
        input: &'a [u8],
        parsed: &mut Parsed,
    ) -> Result<&'a [u8], error::Parse> {
        Ok(parsed.parse_items(input, self)?)
    }
}

#[cfg(feature = "alloc")]
impl sealed::Sealed for OwnedFormatItem {
    fn parse_into<'a>(
        &self,
        input: &'a [u8],
        parsed: &mut Parsed,
    ) -> Result<&'a [u8], error::Parse> {
        Ok(parsed.parse_item(input, self)?)
    }
}

#[cfg(feature = "alloc")]
impl sealed::Sealed for [OwnedFormatItem] {
    fn parse_into<'a>(
        &self,
        input: &'a [u8],
        parsed: &mut Parsed,
    ) -> Result<&'a [u8], error::Parse> {
        Ok(parsed.parse_items(input, self)?)
    }
}

impl<T: Deref> sealed::Sealed for T
where
    T::Target: sealed::Sealed,
{
    fn parse_into<'a>(
        &self,
        input: &'a [u8],
        parsed: &mut Parsed,
    ) -> Result<&'a [u8], error::Parse> {
        self.deref().parse_into(input, parsed)
    }
}
// endregion custom formats

// region: well-known formats
impl sealed::Sealed for Rfc2822 {
    fn parse_into<'a>(
        &self,
        input: &'a [u8],
        parsed: &mut Parsed,
    ) -> Result<&'a [u8], error::Parse> {
        use crate::error::ParseFromDescription::{InvalidComponent, InvalidLiteral};
        use crate::parsing::combinator::rfc::rfc2822::{cfws, fws};
        use crate::parsing::combinator::{
            ascii_char, exactly_n_digits, first_match, n_to_m_digits, opt, sign,
        };

        let colon = ascii_char::<b':'>;
        let comma = ascii_char::<b','>;

        let input = opt(fws)(input).into_inner();
        let input = first_match(
            [
                (b"Mon".as_slice(), Weekday::Monday),
                (b"Tue".as_slice(), Weekday::Tuesday),
                (b"Wed".as_slice(), Weekday::Wednesday),
                (b"Thu".as_slice(), Weekday::Thursday),
                (b"Fri".as_slice(), Weekday::Friday),
                (b"Sat".as_slice(), Weekday::Saturday),
                (b"Sun".as_slice(), Weekday::Sunday),
            ],
            false,
        )(input)
        .and_then(|item| item.consume_value(|value| parsed.set_weekday(value)))
        .ok_or(InvalidComponent("weekday"))?;
        let input = comma(input).ok_or(InvalidLiteral)?.into_inner();
        let input = cfws(input).ok_or(InvalidLiteral)?.into_inner();
        let input = n_to_m_digits::<1, 2, _>(input)
            .and_then(|item| item.consume_value(|value| parsed.set_day(value)))
            .ok_or(InvalidComponent("day"))?;
        let input = cfws(input).ok_or(InvalidLiteral)?.into_inner();
        let input = first_match(
            [
                (b"Jan".as_slice(), Month::January),
                (b"Feb".as_slice(), Month::February),
                (b"Mar".as_slice(), Month::March),
                (b"Apr".as_slice(), Month::April),
                (b"May".as_slice(), Month::May),
                (b"Jun".as_slice(), Month::June),
                (b"Jul".as_slice(), Month::July),
                (b"Aug".as_slice(), Month::August),
                (b"Sep".as_slice(), Month::September),
                (b"Oct".as_slice(), Month::October),
                (b"Nov".as_slice(), Month::November),
                (b"Dec".as_slice(), Month::December),
            ],
            false,
        )(input)
        .and_then(|item| item.consume_value(|value| parsed.set_month(value)))
        .ok_or(InvalidComponent("month"))?;
        let input = cfws(input).ok_or(InvalidLiteral)?.into_inner();
        let input = match exactly_n_digits::<4, u32>(input) {
            Some(item) => {
                let input = item
                    .flat_map(|year| if year >= 1900 { Some(year) } else { None })
                    .and_then(|item| {
                        item.consume_value(|value| parsed.set_year(value.cast_signed()))
                    })
                    .ok_or(InvalidComponent("year"))?;
                fws(input).ok_or(InvalidLiteral)?.into_inner()
            }
            None => {
                let input = exactly_n_digits::<2, u32>(input)
                    .and_then(|item| {
                        item.map(|year| if year < 50 { year + 2000 } else { year + 1900 })
                            .map(|year| year.cast_signed())
                            .consume_value(|value| parsed.set_year(value))
                    })
                    .ok_or(InvalidComponent("year"))?;
                cfws(input).ok_or(InvalidLiteral)?.into_inner()
            }
        };

        let input = exactly_n_digits::<2, _>(input)
            .and_then(|item| item.consume_value(|value| parsed.set_hour_24(value)))
            .ok_or(InvalidComponent("hour"))?;
        let input = opt(cfws)(input).into_inner();
        let input = colon(input).ok_or(InvalidLiteral)?.into_inner();
        let input = opt(cfws)(input).into_inner();
        let input = exactly_n_digits::<2, _>(input)
            .and_then(|item| item.consume_value(|value| parsed.set_minute(value)))
            .ok_or(InvalidComponent("minute"))?;

        let input = if let Some(input) = colon(opt(cfws)(input).into_inner()) {
            let input = input.into_inner(); // discard the colon
            let input = opt(cfws)(input).into_inner();
            let input = exactly_n_digits::<2, _>(input)
                .and_then(|item| item.consume_value(|value| parsed.set_second(value)))
                .ok_or(InvalidComponent("second"))?;
            cfws(input).ok_or(InvalidLiteral)?.into_inner()
        } else {
            cfws(input).ok_or(InvalidLiteral)?.into_inner()
        };

        // The RFC explicitly allows leap seconds.
        parsed.leap_second_allowed = true;

        #[allow(clippy::unnecessary_lazy_evaluations)] // rust-lang/rust-clippy#8522
        let zone_literal = first_match(
            [
                (b"UT".as_slice(), 0),
                (b"GMT".as_slice(), 0),
                (b"EST".as_slice(), -5),
                (b"EDT".as_slice(), -4),
                (b"CST".as_slice(), -6),
                (b"CDT".as_slice(), -5),
                (b"MST".as_slice(), -7),
                (b"MDT".as_slice(), -6),
                (b"PST".as_slice(), -8),
                (b"PDT".as_slice(), -7),
            ],
            false,
        )(input)
        .or_else(|| match input {
            [
                b'a'..=b'i' | b'k'..=b'z' | b'A'..=b'I' | b'K'..=b'Z',
                rest @ ..,
            ] => Some(ParsedItem(rest, 0)),
            _ => None,
        });
        if let Some(zone_literal) = zone_literal {
            let input = zone_literal
                .consume_value(|value| parsed.set_offset_hour(value))
                .ok_or(InvalidComponent("offset hour"))?;
            parsed
                .set_offset_minute_signed(0)
                .ok_or(InvalidComponent("offset minute"))?;
            parsed
                .set_offset_second_signed(0)
                .ok_or(InvalidComponent("offset second"))?;
            return Ok(input);
        }

        let ParsedItem(input, offset_sign) = sign(input).ok_or(InvalidComponent("offset hour"))?;
        let input = exactly_n_digits::<2, u8>(input)
            .and_then(|item| {
                item.map(|offset_hour| {
                    if offset_sign == b'-' {
                        -offset_hour.cast_signed()
                    } else {
                        offset_hour.cast_signed()
                    }
                })
                .consume_value(|value| parsed.set_offset_hour(value))
            })
            .ok_or(InvalidComponent("offset hour"))?;
        let input = exactly_n_digits::<2, u8>(input)
            .and_then(|item| {
                item.consume_value(|value| parsed.set_offset_minute_signed(value.cast_signed()))
            })
            .ok_or(InvalidComponent("offset minute"))?;

        Ok(input)
    }

    fn parse_offset_date_time(&self, input: &[u8]) -> Result<OffsetDateTime, error::Parse> {
        use crate::error::ParseFromDescription::{InvalidComponent, InvalidLiteral};
        use crate::parsing::combinator::rfc::rfc2822::{cfws, fws};
        use crate::parsing::combinator::{
            ascii_char, exactly_n_digits, first_match, n_to_m_digits, opt, sign,
        };

        let colon = ascii_char::<b':'>;
        let comma = ascii_char::<b','>;

        let input = opt(fws)(input).into_inner();
        // This parses the weekday, but we don't actually use the value anywhere. Because of this,
        // just return `()` to avoid unnecessary generated code.
        let ParsedItem(input, ()) = first_match(
            [
                (b"Mon".as_slice(), ()),
                (b"Tue".as_slice(), ()),
                (b"Wed".as_slice(), ()),
                (b"Thu".as_slice(), ()),
                (b"Fri".as_slice(), ()),
                (b"Sat".as_slice(), ()),
                (b"Sun".as_slice(), ()),
            ],
            false,
        )(input)
        .ok_or(InvalidComponent("weekday"))?;
        let input = comma(input).ok_or(InvalidLiteral)?.into_inner();
        let input = cfws(input).ok_or(InvalidLiteral)?.into_inner();
        let ParsedItem(input, day) =
            n_to_m_digits::<1, 2, _>(input).ok_or(InvalidComponent("day"))?;
        let input = cfws(input).ok_or(InvalidLiteral)?.into_inner();
        let ParsedItem(input, month) = first_match(
            [
                (b"Jan".as_slice(), Month::January),
                (b"Feb".as_slice(), Month::February),
                (b"Mar".as_slice(), Month::March),
                (b"Apr".as_slice(), Month::April),
                (b"May".as_slice(), Month::May),
                (b"Jun".as_slice(), Month::June),
                (b"Jul".as_slice(), Month::July),
                (b"Aug".as_slice(), Month::August),
                (b"Sep".as_slice(), Month::September),
                (b"Oct".as_slice(), Month::October),
                (b"Nov".as_slice(), Month::November),
                (b"Dec".as_slice(), Month::December),
            ],
            false,
        )(input)
        .ok_or(InvalidComponent("month"))?;
        let input = cfws(input).ok_or(InvalidLiteral)?.into_inner();
        let (input, year) = match exactly_n_digits::<4, u32>(input) {
            Some(item) => {
                let ParsedItem(input, year) = item
                    .flat_map(|year| if year >= 1900 { Some(year) } else { None })
                    .ok_or(InvalidComponent("year"))?;
                let input = fws(input).ok_or(InvalidLiteral)?.into_inner();
                (input, year)
            }
            None => {
                let ParsedItem(input, year) = exactly_n_digits::<2, u32>(input)
                    .map(|item| item.map(|year| if year < 50 { year + 2000 } else { year + 1900 }))
                    .ok_or(InvalidComponent("year"))?;
                let input = cfws(input).ok_or(InvalidLiteral)?.into_inner();
                (input, year)
            }
        };

        let ParsedItem(input, hour) =
            exactly_n_digits::<2, _>(input).ok_or(InvalidComponent("hour"))?;
        let input = opt(cfws)(input).into_inner();
        let input = colon(input).ok_or(InvalidLiteral)?.into_inner();
        let input = opt(cfws)(input).into_inner();
        let ParsedItem(input, minute) =
            exactly_n_digits::<2, _>(input).ok_or(InvalidComponent("minute"))?;

        let (input, mut second) = if let Some(input) = colon(opt(cfws)(input).into_inner()) {
            let input = input.into_inner(); // discard the colon
            let input = opt(cfws)(input).into_inner();
            let ParsedItem(input, second) =
                exactly_n_digits::<2, _>(input).ok_or(InvalidComponent("second"))?;
            let input = cfws(input).ok_or(InvalidLiteral)?.into_inner();
            (input, second)
        } else {
            (cfws(input).ok_or(InvalidLiteral)?.into_inner(), 0)
        };

        #[allow(clippy::unnecessary_lazy_evaluations)] // rust-lang/rust-clippy#8522
        let zone_literal = first_match(
            [
                (b"UT".as_slice(), 0),
                (b"GMT".as_slice(), 0),
                (b"EST".as_slice(), -5),
                (b"EDT".as_slice(), -4),
                (b"CST".as_slice(), -6),
                (b"CDT".as_slice(), -5),
                (b"MST".as_slice(), -7),
                (b"MDT".as_slice(), -6),
                (b"PST".as_slice(), -8),
                (b"PDT".as_slice(), -7),
            ],
            false,
        )(input)
        .or_else(|| match input {
            [
                b'a'..=b'i' | b'k'..=b'z' | b'A'..=b'I' | b'K'..=b'Z',
                rest @ ..,
            ] => Some(ParsedItem(rest, 0)),
            _ => None,
        });

        let (input, offset_hour, offset_minute) = if let Some(zone_literal) = zone_literal {
            let ParsedItem(input, offset_hour) = zone_literal;
            (input, offset_hour, 0)
        } else {
            let ParsedItem(input, offset_sign) =
                sign(input).ok_or(InvalidComponent("offset hour"))?;
            let ParsedItem(input, offset_hour) = exactly_n_digits::<2, u8>(input)
                .map(|item| {
                    item.map(|offset_hour| {
                        if offset_sign == b'-' {
                            -offset_hour.cast_signed()
                        } else {
                            offset_hour.cast_signed()
                        }
                    })
                })
                .ok_or(InvalidComponent("offset hour"))?;
            let ParsedItem(input, offset_minute) =
                exactly_n_digits::<2, u8>(input).ok_or(InvalidComponent("offset minute"))?;
            (input, offset_hour, offset_minute.cast_signed())
        };

        if !input.is_empty() {
            return Err(error::Parse::ParseFromDescription(
                error::ParseFromDescription::UnexpectedTrailingCharacters,
            ));
        }

        let mut nanosecond = 0;
        let leap_second_input = if second == 60 {
            second = 59;
            nanosecond = 999_999_999;
            true
        } else {
            false
        };

        let dt = (|| {
            let date = Date::from_calendar_date(year.cast_signed(), month, day)?;
            let time = Time::from_hms_nano(hour, minute, second, nanosecond)?;
            let offset = UtcOffset::from_hms(offset_hour, offset_minute, 0)?;
            Ok(OffsetDateTime::new_in_offset(date, time, offset))
        })()
        .map_err(TryFromParsed::ComponentRange)?;

        if leap_second_input && !dt.is_valid_leap_second_stand_in() {
            return Err(error::Parse::TryFromParsed(TryFromParsed::ComponentRange(
                error::ComponentRange {
                    name: "second",
                    minimum: 0,
                    maximum: 59,
                    value: 60,
                    conditional_range: true,
                },
            )));
        }

        Ok(dt)
    }
}

impl sealed::Sealed for Rfc3339 {
    fn parse_into<'a>(
        &self,
        input: &'a [u8],
        parsed: &mut Parsed,
    ) -> Result<&'a [u8], error::Parse> {
        use crate::error::ParseFromDescription::{InvalidComponent, InvalidLiteral};
        use crate::parsing::combinator::{
            any_digit, ascii_char, ascii_char_ignore_case, exactly_n_digits, sign,
        };

        let dash = ascii_char::<b'-'>;
        let colon = ascii_char::<b':'>;

        let input = exactly_n_digits::<4, u32>(input)
            .and_then(|item| item.consume_value(|value| parsed.set_year(value.cast_signed())))
            .ok_or(InvalidComponent("year"))?;
        let input = dash(input).ok_or(InvalidLiteral)?.into_inner();
        let input = exactly_n_digits::<2, _>(input)
            .and_then(|item| item.flat_map(|value| Month::from_number(value).ok()))
            .and_then(|item| item.consume_value(|value| parsed.set_month(value)))
            .ok_or(InvalidComponent("month"))?;
        let input = dash(input).ok_or(InvalidLiteral)?.into_inner();
        let input = exactly_n_digits::<2, _>(input)
            .and_then(|item| item.consume_value(|value| parsed.set_day(value)))
            .ok_or(InvalidComponent("day"))?;
        let input = ascii_char_ignore_case::<b'T'>(input)
            .ok_or(InvalidLiteral)?
            .into_inner();
        let input = exactly_n_digits::<2, _>(input)
            .and_then(|item| item.consume_value(|value| parsed.set_hour_24(value)))
            .ok_or(InvalidComponent("hour"))?;
        let input = colon(input).ok_or(InvalidLiteral)?.into_inner();
        let input = exactly_n_digits::<2, _>(input)
            .and_then(|item| item.consume_value(|value| parsed.set_minute(value)))
            .ok_or(InvalidComponent("minute"))?;
        let input = colon(input).ok_or(InvalidLiteral)?.into_inner();
        let input = exactly_n_digits::<2, _>(input)
            .and_then(|item| item.consume_value(|value| parsed.set_second(value)))
            .ok_or(InvalidComponent("second"))?;
        let input = if let Some(ParsedItem(input, ())) = ascii_char::<b'.'>(input) {
            let ParsedItem(mut input, mut value) = any_digit(input)
                .ok_or(InvalidComponent("subsecond"))?
                .map(|v| (v - b'0').extend::<u32>() * 100_000_000);

            let mut multiplier = 10_000_000;
            while let Some(ParsedItem(new_input, digit)) = any_digit(input) {
                value += (digit - b'0').extend::<u32>() * multiplier;
                input = new_input;
                multiplier /= 10;
            }

            parsed
                .set_subsecond(value)
                .ok_or(InvalidComponent("subsecond"))?;
            input
        } else {
            input
        };

        // The RFC explicitly allows leap seconds.
        parsed.leap_second_allowed = true;

        if let Some(ParsedItem(input, ())) = ascii_char_ignore_case::<b'Z'>(input) {
            parsed
                .set_offset_hour(0)
                .ok_or(InvalidComponent("offset hour"))?;
            parsed
                .set_offset_minute_signed(0)
                .ok_or(InvalidComponent("offset minute"))?;
            parsed
                .set_offset_second_signed(0)
                .ok_or(InvalidComponent("offset second"))?;
            return Ok(input);
        }

        let ParsedItem(input, offset_sign) = sign(input).ok_or(InvalidComponent("offset hour"))?;
        let input = exactly_n_digits::<2, u8>(input)
            .and_then(|item| {
                item.filter(|&offset_hour| offset_hour <= 23)?
                    .map(|offset_hour| {
                        if offset_sign == b'-' {
                            -offset_hour.cast_signed()
                        } else {
                            offset_hour.cast_signed()
                        }
                    })
                    .consume_value(|value| parsed.set_offset_hour(value))
            })
            .ok_or(InvalidComponent("offset hour"))?;
        let input = colon(input).ok_or(InvalidLiteral)?.into_inner();
        let input = exactly_n_digits::<2, u8>(input)
            .and_then(|item| {
                item.map(|offset_minute| {
                    if offset_sign == b'-' {
                        -offset_minute.cast_signed()
                    } else {
                        offset_minute.cast_signed()
                    }
                })
                .consume_value(|value| parsed.set_offset_minute_signed(value))
            })
            .ok_or(InvalidComponent("offset minute"))?;

        Ok(input)
    }

    fn parse_offset_date_time(&self, input: &[u8]) -> Result<OffsetDateTime, error::Parse> {
        use crate::error::ParseFromDescription::{InvalidComponent, InvalidLiteral};
        use crate::parsing::combinator::{
            any_digit, ascii_char, ascii_char_ignore_case, exactly_n_digits, sign,
        };

        let dash = ascii_char::<b'-'>;
        let colon = ascii_char::<b':'>;

        let ParsedItem(input, year) =
            exactly_n_digits::<4, u32>(input).ok_or(InvalidComponent("year"))?;
        let input = dash(input).ok_or(InvalidLiteral)?.into_inner();
        let ParsedItem(input, month) =
            exactly_n_digits::<2, _>(input).ok_or(InvalidComponent("month"))?;
        let input = dash(input).ok_or(InvalidLiteral)?.into_inner();
        let ParsedItem(input, day) =
            exactly_n_digits::<2, _>(input).ok_or(InvalidComponent("day"))?;
        let input = ascii_char_ignore_case::<b'T'>(input)
            .ok_or(InvalidLiteral)?
            .into_inner();
        let ParsedItem(input, hour) =
            exactly_n_digits::<2, _>(input).ok_or(InvalidComponent("hour"))?;
        let input = colon(input).ok_or(InvalidLiteral)?.into_inner();
        let ParsedItem(input, minute) =
            exactly_n_digits::<2, _>(input).ok_or(InvalidComponent("minute"))?;
        let input = colon(input).ok_or(InvalidLiteral)?.into_inner();
        let ParsedItem(input, mut second) =
            exactly_n_digits::<2, _>(input).ok_or(InvalidComponent("second"))?;
        let ParsedItem(input, mut nanosecond) =
            if let Some(ParsedItem(input, ())) = ascii_char::<b'.'>(input) {
                let ParsedItem(mut input, mut value) = any_digit(input)
                    .ok_or(InvalidComponent("subsecond"))?
                    .map(|v| (v - b'0').extend::<u32>() * 100_000_000);

                let mut multiplier = 10_000_000;
                while let Some(ParsedItem(new_input, digit)) = any_digit(input) {
                    value += (digit - b'0').extend::<u32>() * multiplier;
                    input = new_input;
                    multiplier /= 10;
                }

                ParsedItem(input, value)
            } else {
                ParsedItem(input, 0)
            };
        let ParsedItem(input, offset) = {
            if let Some(ParsedItem(input, ())) = ascii_char_ignore_case::<b'Z'>(input) {
                ParsedItem(input, UtcOffset::UTC)
            } else {
                let ParsedItem(input, offset_sign) =
                    sign(input).ok_or(InvalidComponent("offset hour"))?;
                let ParsedItem(input, offset_hour) = exactly_n_digits::<2, u8>(input)
                    .and_then(|parsed| parsed.filter(|&offset_hour| offset_hour <= 23))
                    .ok_or(InvalidComponent("offset hour"))?;
                let input = colon(input).ok_or(InvalidLiteral)?.into_inner();
                let ParsedItem(input, offset_minute) =
                    exactly_n_digits::<2, u8>(input).ok_or(InvalidComponent("offset minute"))?;
                UtcOffset::from_hms(
                    if offset_sign == b'-' {
                        -offset_hour.cast_signed()
                    } else {
                        offset_hour.cast_signed()
                    },
                    if offset_sign == b'-' {
                        -offset_minute.cast_signed()
                    } else {
                        offset_minute.cast_signed()
                    },
                    0,
                )
                .map(|offset| ParsedItem(input, offset))
                .map_err(|mut err| {
                    // Provide the user a more accurate error.
                    if err.name == "hours" {
                        err.name = "offset hour";
                    } else if err.name == "minutes" {
                        err.name = "offset minute";
                    }
                    err
                })
                .map_err(TryFromParsed::ComponentRange)?
            }
        };

        if !input.is_empty() {
            return Err(error::Parse::ParseFromDescription(
                error::ParseFromDescription::UnexpectedTrailingCharacters,
            ));
        }

        // The RFC explicitly permits leap seconds. We don't currently support them, so treat it as
        // the preceding nanosecond. However, leap seconds can only occur as the last second of the
        // month UTC.
        let leap_second_input = if second == 60 {
            second = 59;
            nanosecond = 999_999_999;
            true
        } else {
            false
        };

        let date = Month::from_number(month)
            .and_then(|month| Date::from_calendar_date(year.cast_signed(), month, day))
            .map_err(TryFromParsed::ComponentRange)?;
        let time = Time::from_hms_nano(hour, minute, second, nanosecond)
            .map_err(TryFromParsed::ComponentRange)?;
        let dt = OffsetDateTime::new_in_offset(date, time, offset);

        if leap_second_input && !dt.is_valid_leap_second_stand_in() {
            return Err(error::Parse::TryFromParsed(TryFromParsed::ComponentRange(
                error::ComponentRange {
                    name: "second",
                    minimum: 0,
                    maximum: 59,
                    value: 60,
                    conditional_range: true,
                },
            )));
        }

        Ok(dt)
    }
}

impl<const CONFIG: EncodedConfig> sealed::Sealed for Iso8601<CONFIG> {
    fn parse_into<'a>(
        &self,
        mut input: &'a [u8],
        parsed: &mut Parsed,
    ) -> Result<&'a [u8], error::Parse> {
        use crate::parsing::combinator::rfc::iso8601::ExtendedKind;

        let mut extended_kind = ExtendedKind::Unknown;
        let mut date_is_present = false;
        let mut time_is_present = false;
        let mut offset_is_present = false;
        let mut first_error = None;

        match Self::parse_date(parsed, &mut extended_kind)(input) {
            Ok(new_input) => {
                input = new_input;
                date_is_present = true;
            }
            Err(err) => {
                first_error.get_or_insert(err);
            }
        }

        match Self::parse_time(parsed, &mut extended_kind, date_is_present)(input) {
            Ok(new_input) => {
                input = new_input;
                time_is_present = true;
            }
            Err(err) => {
                first_error.get_or_insert(err);
            }
        }

        // If a date and offset are present, a time must be as well.
        if !date_is_present || time_is_present {
            match Self::parse_offset(parsed, &mut extended_kind)(input) {
                Ok(new_input) => {
                    input = new_input;
                    offset_is_present = true;
                }
                Err(err) => {
                    first_error.get_or_insert(err);
                }
            }
        }

        if !date_is_present && !time_is_present && !offset_is_present {
            match first_error {
                Some(err) => return Err(err),
                None => bug!("an error should be present if no components were parsed"),
            }
        }

        Ok(input)
    }
}
// endregion well-known formats
