// Copyright (c) 2012, the Dart project authors.  Please see the AUTHORS file
// for details. All rights reserved. Use of this source code is governed by a
// BSD-style license that can be found in the LICENSE file.

import 'package:intl/date_symbols.dart';
import 'package:intl/src/date_format_internal.dart';
import 'package:intl/src/intl_helpers.dart' as helpers;
import 'package:meta/meta.dart';

import 'constants.dart' as constants;
import 'date_builder.dart';
import 'date_computation.dart' as date_computation;
import 'intl_stream.dart';
import 'regexp.dart' as regexp;

part 'date_format_field.dart';

// Suppress naming issues as changes would breaking.
// ignore_for_file: non_constant_identifier_names, constant_identifier_names

// TODO(efortuna): Customized pattern system -- suggested by i18n needs
// feedback on appropriateness.
/// DateFormat is for formatting and parsing dates in a locale-sensitive
/// manner.
///
/// It allows the user to choose from a set of standard date time formats as
/// well as specify a customized pattern under certain locales. Date elements
/// that vary across locales include month name, week name, field order, etc.
/// We also allow the user to use any customized pattern to parse or format
/// date-time strings under certain locales. Date elements that vary across
/// locales include month name, weekname, field, order, etc.
///
/// Formatting dates in the default 'en_US' format does not require any
/// initialization. e.g.
///
/// ```dart
/// print(DateFormat.yMMMd().format(DateTime.now()));
/// ```
///
/// But for other locales, the formatting data for the locale must be
/// obtained. This can currently be done in one of three ways, determined by
/// which library you import. In all cases, the 'initializeDateFormatting'
/// method must be called and will return a future that is complete once the
/// locale data is available. The result of the future isn't important, but the
/// data for that locale is available to the date formatting and parsing once it
/// completes.
///
/// The easiest option is that the data may be available locally, imported in a
/// library that contains data for all the locales.
///
/// ```dart
/// import 'package:intl/date_symbol_data_local.dart';
/// initializeDateFormatting('fr_FR', null).then((_) => runMyCode());
/// ```
///
/// If we are running outside of a browser, we may want to read the data
/// from files in the file system.
///
/// ```dart
/// import 'package:intl/date_symbol_data_file.dart';
/// initializeDateFormatting('de_DE', null).then((_) => runMyCode());
/// ```
///
/// If we are running in a browser, we may want to read the data from the
/// server using the XmlHttpRequest mechanism.
///
/// ```dart
/// import 'package:intl/date_symbol_data_http_request.dart';
/// initializeDateFormatting('pt_BR', null).then((_) => runMyCode());
/// ```
///
/// Once we have the locale data, we need to specify the particular format.
/// This library uses the ICU/JDK date/time pattern specification both for
/// complete format specifications and also the abbreviated 'skeleton' form
/// which can also adapt to different locales and is preferred where available.
///
/// Skeletons: These can be specified either as the ICU constant name or as the
/// skeleton to which it resolves. The supported set of skeletons is as follows.
/// For each skeleton there is a named constructor that can be used to create
/// it.  It's also possible to pass the skeleton as a string, but the
/// constructor is preferred.
///
///      ICU Name                   Skeleton
///      --------                   --------
///      DAY                          d
///      ABBR_WEEKDAY                 E
///      WEEKDAY                      EEEE
///      ABBR_STANDALONE_MONTH        LLL
///      STANDALONE_MONTH             LLLL
///      NUM_MONTH                    M
///      NUM_MONTH_DAY                Md
///      NUM_MONTH_WEEKDAY_DAY        MEd
///      ABBR_MONTH                   MMM
///      ABBR_MONTH_DAY               MMMd
///      ABBR_MONTH_WEEKDAY_DAY       MMMEd
///      MONTH                        MMMM
///      MONTH_DAY                    MMMMd
///      MONTH_WEEKDAY_DAY            MMMMEEEEd
///      ABBR_QUARTER                 QQQ
///      QUARTER                      QQQQ
///      YEAR                         y
///      YEAR_NUM_MONTH               yM
///      YEAR_NUM_MONTH_DAY           yMd
///      YEAR_NUM_MONTH_WEEKDAY_DAY   yMEd
///      YEAR_ABBR_MONTH              yMMM
///      YEAR_ABBR_MONTH_DAY          yMMMd
///      YEAR_ABBR_MONTH_WEEKDAY_DAY  yMMMEd
///      YEAR_MONTH                   yMMMM
///      YEAR_MONTH_DAY               yMMMMd
///      YEAR_MONTH_WEEKDAY_DAY       yMMMMEEEEd
///      YEAR_ABBR_QUARTER            yQQQ
///      YEAR_QUARTER                 yQQQQ
///      HOUR24                       H
///      HOUR24_MINUTE                Hm
///      HOUR24_MINUTE_SECOND         Hms
///      HOUR                         j
///      HOUR_MINUTE                  jm
///      HOUR_MINUTE_SECOND           jms
///      HOUR_MINUTE_GENERIC_TZ       jmv   (not yet implemented)
///      HOUR_MINUTE_TZ               jmz   (not yet implemented)
///      HOUR_GENERIC_TZ              jv    (not yet implemented)
///      HOUR_TZ                      jz    (not yet implemented)
///      MINUTE                       m
///      MINUTE_SECOND                ms
///      SECOND                       s
//
// TODO(https://github.com/dart-lang/intl/issues/74): Update table above.
///
/// Examples Using the US Locale:
///
///      Pattern                           Result
///      ----------------                  -------
///      DateFormat.yMd()                 -> 7/10/1996
///      DateFormat('yMd')                -> 7/10/1996
///      DateFormat.yMMMMd('en_US')       -> July 10, 1996
///      DateFormat.jm()                  -> 5:08 PM
///      DateFormat.yMd().add_jm()        -> 7/10/1996 5:08 PM
///      DateFormat.Hm()                  -> 17:08 // force 24 hour time
///
/// Explicit Pattern Syntax: Formats can also be specified with a pattern
/// string.  This can be used for formats that don't have a skeleton available,
/// but these will not adapt to different locales. For example, in an explicit
/// pattern the letters 'H' and 'h' are available for 24 hour and 12 hour time
/// formats respectively. But there isn't a way in an explicit pattern to get
/// the behaviour of the 'j' skeleton, which prints 24 hour or 12 hour time
/// according to the conventions of the locale, and also includes am/pm markers
/// where appropriate. So it is preferable to use the skeletons.
///
/// The following characters are available in explicit patterns:
///
///     Symbol   Meaning                Presentation       Example
///     ------   -------                ------------       -------
///     G        era designator         (Text)             AD
///     y        year                   (Number)           1996
///     M        month in year          (Text & Number)    July & 07
///     L        standalone month       (Text & Number)    July & 07
///     d        day in month           (Number)           10
///     c        standalone day         (Number)           10
///     h        hour in am/pm (1~12)   (Number)           12
///     H        hour in day (0~23)     (Number)           0
///     m        minute in hour         (Number)           30
///     s        second in minute       (Number)           55
///     S        fractional second      (Number)           978
///     E        day of week            (Text)             Tuesday
///     D        day in year            (Number)           189
///     a        am/pm marker           (Text)             PM
///     k        hour in day (1~24)     (Number)           24
///     K        hour in am/pm (0~11)   (Number)           0
///     Q        quarter                (Text)             Q3
///     '        escape for text        (Delimiter)        'Date='
///     ''       single quote           (Literal)          'o''clock'
///
//  TODO(https://github.com/dart-lang/intl/issues/74): Merge tables.
//
/// The following characters are reserved and currently are unimplemented:
///
///     Symbol   Meaning                Presentation       Example
///     ------   -------                ------------       -------
///     z        time zone              (Text)             Pacific Standard Time
///     Z        time zone (RFC 822)    (Number)           -0800
///     v        time zone (generic)    (Text)             Pacific Time
///
/// The count of pattern letters determine the format.
///
/// **Text**:
/// * 5 pattern letters--use narrow form for standalone. Otherwise not used.
/// * 4 or more pattern letters--use full form,
/// * 3 pattern letters--use short or abbreviated form if one exists
/// * less than 3--use numeric form if one exists
///
/// **Number**: the minimum number of digits. Shorter numbers are zero-padded to
/// this amount (e.g. if 'm' produces '6', 'mm' produces '06'). Year is handled
/// specially; that is, if the count of 'y' is 2, the Year will be truncated to
/// 2 digits. (e.g., if 'yyyy' produces '1997', 'yy' produces '97'.) Unlike
/// other fields, fractional seconds are padded on the right with zero.
///
/// **(Text & Number)**: 3 or over, use text, otherwise use number.
///
/// Any characters not in the pattern will be treated as quoted text. For
/// instance, characters like ':', '.', ' ', '#' and '@' will appear in the
/// resulting text even though they are not enclosed in single quotes. In our
/// current pattern usage, not all letters have meanings. But those unused
/// letters are strongly discouraged to be used as quoted text without quotes,
/// because we may use other letters as pattern characters in the future.
///
/// Examples Using the US Locale:
///
///     Format Pattern                    Result
///     --------------                    -------
///     'EEE, MMM d, ''yy'                Wed, Jul 10, '96
///     'h:mm a'                          12:08 PM
///     'yyyyy.MMMMM.dd GGG hh:mm aaa'    01996.July.10 AD 12:08 PM
//
// TODO(https://github.com/dart-lang/intl/issues/74): Merge tables.
//
//      NOT YET IMPLEMENTED
//      -------------------
//      'yyyy.MM.dd G 'at' HH:mm:ss vvvv' 1996.07.10 AD at 15:08:56 Pacific Time
//      'hh 'o''clock' a, zzzz'           12 o'clock PM, Pacific Daylight Time
//      'K:mm a, vvv'                     0:00 PM, PT
///
/// When parsing a date string using the abbreviated year pattern ('yy'),
/// DateFormat must interpret the abbreviated year relative to some
/// century. It does this by adjusting dates to be within 80 years before and 20
/// years after the time the parse function is called. For example, using a
/// pattern of 'MM/dd/yy' and a DateFormat instance created on Jan 1, 1997,
/// the string '01/11/12' would be interpreted as Jan 11, 2012 while the string
/// '05/04/64' would be interpreted as May 4, 1964. During parsing, only
/// strings consisting of exactly two digits will be parsed into the default
/// century. Any other numeric string, such as a one digit string, a three or
/// more digit string will be interpreted as its face value. Tests that parse
/// two-digit years can control the current date with package:clock.
///
/// If the year pattern does not have exactly two 'y' characters, the year is
/// interpreted literally, regardless of the number of digits. So using the
/// pattern 'MM/dd/yyyy', '01/11/12' parses to Jan 11, 12 A.D.

class DateFormat {
  /// Creates a new DateFormat, using the format specified by [newPattern].
  ///
  /// For forms that match one of our predefined skeletons, we look up the
  /// corresponding pattern in [locale] (or in the default locale if none is
  /// specified) and use the resulting full format string. This is the preferred
  /// usage, but if [newPattern] does not match one of the skeletons, then it is
  /// used as a format directly, but will not be adapted to suit the locale.
  ///
  /// For example, in an en_US locale, specifying the skeleton
  ///
  /// ```dart
  /// DateFormat.yMEd();
  /// ```
  ///
  /// or the explicit
  ///
  /// ```dart
  /// DateFormat('EEE, M/d/y');
  /// ```
  ///
  /// would produce the same result, a date of the form 'Wed, 6/27/2012'.
  ///
  /// The first version would produce a different format string if used in
  /// another locale, but the second format would always be the same.
  ///
  /// If [locale] does not exist in our set of supported locales then an
  /// [ArgumentError] is thrown.
  DateFormat([String? newPattern, String? locale])
      : _locale = helpers.verifiedLocale(locale, localeExists, null)! {
    // TODO(alanknight): It should be possible to specify multiple skeletons eg
    // date, time, timezone all separately. Adding many or named parameters to
    // the constructor seems awkward, especially with the possibility of
    // confusion with the locale. A 'fluent' interface with cascading on an
    // instance might work better? A list of patterns is also possible.
    addPattern(newPattern);
  }

  /// Allows specifying a different way of creating a DateTime instance for
  /// testing.
  ///
  /// There can be rare and erratic errors in DateTime creation in both
  /// JavaScript and the Dart VM, and this allows us to test ways of
  /// compensating for them.
  @visibleForTesting
  @Deprecated('clients should not depend on this internal field')
  // ignore: library_private_types_in_public_api
  _DateTimeConstructor dateTimeConstructor = (int year, int month, int day,
      int hour24, int minute, int second, int fractionalSecond, bool utc) {
    if (utc) {
      return DateTime.utc(
          year, month, day, hour24, minute, second, fractionalSecond);
    } else {
      return DateTime(
          year, month, day, hour24, minute, second, fractionalSecond);
    }
  };

  /// Return a string representing [date] formatted according to our locale
  /// and internal format.
  String format(DateTime date) {
    // TODO(efortuna): read optional TimeZone argument (or similar)?
    var result = StringBuffer();
    for (var field in _formatFields) {
      result.write(field.format(date));
    }
    return result.toString();
  }

  /// NOT YET IMPLEMENTED.
  ///
  /// Returns a date string indicating how long ago (3 hours, 2 minutes)
  /// something has happened or how long in the future something will happen
  /// given a [reference] DateTime relative to the current time.
  String formatDuration(DateTime reference) => '';

  /// NOT YET IMPLEMENTED.
  ///
  /// Formats a string indicating how long ago (negative [duration]) or how far
  /// in the future (positive [duration]) some time is with respect to a
  /// reference [date].
  String formatDurationFrom(Duration duration, DateTime date) => '';

  /// Given user input, attempt to parse the [inputString] into the anticipated
  /// format, treating it as being in the local timezone.
  ///
  /// If [inputString] does not match our format, throws a [FormatException].
  /// This will accept dates whose values are not strictly valid, or strings
  /// with additional characters (including whitespace) after a valid date. For
  /// stricter parsing, use [parseStrict].
  DateTime parse(String inputString, [bool utc = false]) =>
      _parse(inputString, utc: utc, strict: false);

  /// Given user input, attempt to parse the [inputString] 'loosely' into the
  /// anticipated format, accepting some variations from the strict format.
  ///
  /// If [inputString] is accepted by [parseStrict], just return the result. If
  /// not, attempt to parse it, but accepting either upper or lower case,
  /// allowing delimiters to be missing and replaced or supplemented with
  /// whitespace, and allowing arbitrary amounts of whitespace wherever
  /// whitespace is permitted. Note that this does not allow trailing
  /// characters, the way [parse] does.  It also does not allow alternative
  /// names for months or weekdays other than those the format knows about. The
  /// restrictions are quite arbitrary and it's not known how well they'll work
  /// for locales that aren't English-like.
  ///
  /// If [inputString] does not parse, this throws a [FormatException].
  ///
  /// For example, this will accept
  ///
  ///       DateFormat.yMMMd('en_US').parseLoose('SEp   3 2014');
  ///       DateFormat.yMd('en_US').parseLoose('09    03/2014');
  ///       DateFormat.yMd('en_US').parseLoose('09 / 03 / 2014');
  ///
  /// It will NOT accept
  ///
  ///       // 'Sept' is not a valid month name.
  ///       DateFormat.yMMMd('en_US').parseLoose('Sept 3, 2014');
  DateTime parseLoose(String inputString, [bool utc = false]) {
    try {
      return _parse(inputString, utc: utc, strict: true);
    } on FormatException {
      return _parseLoose(inputString.toLowerCase(), utc);
    }
  }

  DateTime _parseLoose(String inputString, bool utc) {
    var dateFields = DateBuilder(locale, dateTimeConstructor);
    if (utc) dateFields.utc = true;
    var stream = IntlStream(inputString);
    for (var field in _formatFields) {
      field.parseLoose(stream, dateFields);
    }
    if (!stream.atEnd()) {
      throw FormatException(
          'Characters remaining after date parsing in $inputString');
    }
    dateFields.verify(inputString);
    return dateFields.asDate();
  }

  /// Given user input, attempt to parse the [inputString] into the anticipated
  /// format, treating it as being in the local timezone.
  ///
  /// If [inputString] does not match our format, throws a [FormatException].
  /// This will reject dates whose values are not strictly valid, even if the
  /// DateTime constructor will accept them. It will also reject strings with
  /// additional characters (including whitespace) after a valid date. For
  /// looser parsing, use [parse].
  DateTime parseStrict(String inputString, [bool utc = false]) =>
      _parse(inputString, utc: utc, strict: true);

  DateTime _parse(String inputString, {bool utc = false, bool strict = false}) {
    // TODO(alanknight): The Closure code refers to special parsing of numeric
    // values with no delimiters, which we currently don't do. Should we?
    var dateFields = DateBuilder(locale, dateTimeConstructor);
    if (utc) dateFields.utc = true;
    dateFields.dateOnly = dateOnly;
    var stream = IntlStream(inputString);
    for (var field in _formatFields) {
      field.parse(stream, dateFields);
    }
    if (strict && !stream.atEnd()) {
      throw FormatException(
          'Characters remaining after date parsing in $inputString');
    }
    if (strict) dateFields.verify(inputString);
    return dateFields.asDate();
  }

  /// Does our format only only date fields, and no time fields.
  ///
  /// For example, 'yyyy-MM-dd' would be true, but 'dd hh:mm' would be false.
  bool get dateOnly => _dateOnly ??= _checkDateOnly;
  bool? _dateOnly;
  bool get _checkDateOnly => _formatFields.every((each) => each.forDate);

  /// Given user input, attempt to parse the [inputString] into the anticipated
  /// format, treating it as being in UTC.
  ///
  /// The canonical Dart style name
  /// is [parseUtc], but [parseUTC] is retained
  /// for backward-compatibility.
  DateTime parseUTC(String inputString) => parse(inputString, true);

  /// Given user input, attempt to parse the [inputString] into the anticipated
  /// format, treating it as being in UTC.
  ///
  /// The canonical Dart style name
  /// is [parseUtc], but [parseUTC] is retained
  /// for backward-compatibility.
  DateTime parseUtc(String inputString) => parse(inputString, true);

  /// Return the locale code in which we operate, e.g. 'en_US' or 'pt'.
  String get locale => _locale;

  /// Returns a list of all locales for which we have date formatting
  /// information.
  static List<String> allLocalesWithSymbols() =>
      List<String>.from(dateTimeSymbols.keys);

  /// The named constructors for this class are all conveniences for creating
  /// instances using one of the known 'skeleton' formats, and having code
  /// completion support for discovering those formats.
  /// So,
  ///
  /// ```dart
  /// DateFormat.yMd('en_US')
  /// ```
  ///
  /// is equivalent to
  ///
  /// ```dart
  /// DateFormat('yMd', 'en_US')
  /// ```
  ///
  /// To create a compound format you can use these constructors in combination
  /// with the 'add_*' methods below. e.g.
  ///
  /// ```dart
  /// DateFormat.yMd().add_Hms();
  /// ```
  ///
  /// If the optional [locale] is omitted, the format will be created using the
  /// default locale in [Intl.systemLocale].
  DateFormat.d([locale]) : this('d', locale);
  DateFormat.E([locale]) : this('E', locale);
  DateFormat.EEEE([locale]) : this('EEEE', locale);
  DateFormat.LLL([locale]) : this('LLL', locale);
  DateFormat.LLLL([locale]) : this('LLLL', locale);
  DateFormat.M([locale]) : this('M', locale);
  DateFormat.Md([locale]) : this('Md', locale);
  DateFormat.MEd([locale]) : this('MEd', locale);
  DateFormat.MMM([locale]) : this('MMM', locale);
  DateFormat.MMMd([locale]) : this('MMMd', locale);
  DateFormat.MMMEd([locale]) : this('MMMEd', locale);
  DateFormat.MMMM([locale]) : this('MMMM', locale);
  DateFormat.MMMMd([locale]) : this('MMMMd', locale);
  DateFormat.MMMMEEEEd([locale]) : this('MMMMEEEEd', locale);
  DateFormat.QQQ([locale]) : this('QQQ', locale);
  DateFormat.QQQQ([locale]) : this('QQQQ', locale);
  DateFormat.y([locale]) : this('y', locale);
  DateFormat.yM([locale]) : this('yM', locale);
  DateFormat.yMd([locale]) : this('yMd', locale);
  DateFormat.yMEd([locale]) : this('yMEd', locale);
  DateFormat.yMMM([locale]) : this('yMMM', locale);
  DateFormat.yMMMd([locale]) : this('yMMMd', locale);
  DateFormat.yMMMEd([locale]) : this('yMMMEd', locale);
  DateFormat.yMMMM([locale]) : this('yMMMM', locale);
  DateFormat.yMMMMd([locale]) : this('yMMMMd', locale);
  DateFormat.yMMMMEEEEd([locale]) : this('yMMMMEEEEd', locale);
  DateFormat.yQQQ([locale]) : this('yQQQ', locale);
  DateFormat.yQQQQ([locale]) : this('yQQQQ', locale);
  DateFormat.H([locale]) : this('H', locale);
  DateFormat.Hm([locale]) : this('Hm', locale);
  DateFormat.Hms([locale]) : this('Hms', locale);
  DateFormat.j([locale]) : this('j', locale);
  DateFormat.jm([locale]) : this('jm', locale);
  DateFormat.jms([locale]) : this('jms', locale);

  /// NOT YET IMPLEMENTED.
  // TODO(https://github.com/dart-lang/intl/issues/74)
  DateFormat.jmv([locale]) : this('jmv', locale);

  /// NOT YET IMPLEMENTED.
  // TODO(https://github.com/dart-lang/intl/issues/74)
  DateFormat.jmz([locale]) : this('jmz', locale);

  /// NOT YET IMPLEMENTED.
  // TODO(https://github.com/dart-lang/intl/issues/74)
  DateFormat.jv([locale]) : this('jv', locale);

  /// NOT YET IMPLEMENTED.
  // TODO(https://github.com/dart-lang/intl/issues/74)
  DateFormat.jz([locale]) : this('jz', locale);
  DateFormat.m([locale]) : this('m', locale);
  DateFormat.ms([locale]) : this('ms', locale);
  DateFormat.s([locale]) : this('s', locale);

  /// The 'add_*' methods append a particular skeleton to the format, or set
  /// it as the only format if none was previously set. These are primarily
  /// useful for creating compound formats. For example
  ///
  /// ```dart
  /// DateFormat.yMd().add_Hms();
  /// ```
  ///
  /// would create a date format that prints both the date and the time.
  DateFormat add_d() => addPattern('d');
  DateFormat add_E() => addPattern('E');
  DateFormat add_EEEE() => addPattern('EEEE');
  DateFormat add_LLL() => addPattern('LLL');
  DateFormat add_LLLL() => addPattern('LLLL');
  DateFormat add_M() => addPattern('M');
  DateFormat add_Md() => addPattern('Md');
  DateFormat add_MEd() => addPattern('MEd');
  DateFormat add_MMM() => addPattern('MMM');
  DateFormat add_MMMd() => addPattern('MMMd');
  DateFormat add_MMMEd() => addPattern('MMMEd');
  DateFormat add_MMMM() => addPattern('MMMM');
  DateFormat add_MMMMd() => addPattern('MMMMd');
  DateFormat add_MMMMEEEEd() => addPattern('MMMMEEEEd');
  DateFormat add_QQQ() => addPattern('QQQ');
  DateFormat add_QQQQ() => addPattern('QQQQ');
  DateFormat add_y() => addPattern('y');
  DateFormat add_yM() => addPattern('yM');
  DateFormat add_yMd() => addPattern('yMd');
  DateFormat add_yMEd() => addPattern('yMEd');
  DateFormat add_yMMM() => addPattern('yMMM');
  DateFormat add_yMMMd() => addPattern('yMMMd');
  DateFormat add_yMMMEd() => addPattern('yMMMEd');
  DateFormat add_yMMMM() => addPattern('yMMMM');
  DateFormat add_yMMMMd() => addPattern('yMMMMd');
  DateFormat add_yMMMMEEEEd() => addPattern('yMMMMEEEEd');
  DateFormat add_yQQQ() => addPattern('yQQQ');
  DateFormat add_yQQQQ() => addPattern('yQQQQ');
  DateFormat add_H() => addPattern('H');
  DateFormat add_Hm() => addPattern('Hm');
  DateFormat add_Hms() => addPattern('Hms');
  DateFormat add_j() => addPattern('j');
  DateFormat add_jm() => addPattern('jm');
  DateFormat add_jms() => addPattern('jms');

  /// NOT YET IMPLEMENTED.
  // TODO(https://github.com/dart-lang/intl/issues/74)
  DateFormat add_jmv() => addPattern('jmv');

  /// NOT YET IMPLEMENTED.
  // TODO(https://github.com/dart-lang/intl/issues/74)
  DateFormat add_jmz() => addPattern('jmz');

  /// NOT YET IMPLEMENTED.
  // TODO(https://github.com/dart-lang/intl/issues/74)
  DateFormat add_jv() => addPattern('jv');

  /// NOT YET IMPLEMENTED.
  // TODO(https://github.com/dart-lang/intl/issues/74)
  DateFormat add_jz() => addPattern('jz');
  DateFormat add_m() => addPattern('m');
  DateFormat add_ms() => addPattern('ms');
  DateFormat add_s() => addPattern('s');

  /// For each of the skeleton formats we also allow the use of the
  /// corresponding ICU constant names.
  static const String ABBR_MONTH = 'MMM';
  static const String DAY = 'd';
  static const String ABBR_WEEKDAY = 'E';
  static const String WEEKDAY = 'EEEE';
  static const String ABBR_STANDALONE_MONTH = 'LLL';
  static const String STANDALONE_MONTH = 'LLLL';
  static const String NUM_MONTH = 'M';
  static const String NUM_MONTH_DAY = 'Md';
  static const String NUM_MONTH_WEEKDAY_DAY = 'MEd';
  static const String ABBR_MONTH_DAY = 'MMMd';
  static const String ABBR_MONTH_WEEKDAY_DAY = 'MMMEd';
  static const String MONTH = 'MMMM';
  static const String MONTH_DAY = 'MMMMd';
  static const String MONTH_WEEKDAY_DAY = 'MMMMEEEEd';
  static const String ABBR_QUARTER = 'QQQ';
  static const String QUARTER = 'QQQQ';
  static const String YEAR = 'y';
  static const String YEAR_NUM_MONTH = 'yM';
  static const String YEAR_NUM_MONTH_DAY = 'yMd';
  static const String YEAR_NUM_MONTH_WEEKDAY_DAY = 'yMEd';
  static const String YEAR_ABBR_MONTH = 'yMMM';
  static const String YEAR_ABBR_MONTH_DAY = 'yMMMd';
  static const String YEAR_ABBR_MONTH_WEEKDAY_DAY = 'yMMMEd';
  static const String YEAR_MONTH = 'yMMMM';
  static const String YEAR_MONTH_DAY = 'yMMMMd';
  static const String YEAR_MONTH_WEEKDAY_DAY = 'yMMMMEEEEd';
  static const String YEAR_ABBR_QUARTER = 'yQQQ';
  static const String YEAR_QUARTER = 'yQQQQ';
  static const String HOUR24 = 'H';
  static const String HOUR24_MINUTE = 'Hm';
  static const String HOUR24_MINUTE_SECOND = 'Hms';
  static const String HOUR = 'j';
  static const String HOUR_MINUTE = 'jm';
  static const String HOUR_MINUTE_SECOND = 'jms';

  /// NOT YET IMPLEMENTED.
  // TODO(https://github.com/dart-lang/intl/issues/74)
  static const String HOUR_MINUTE_GENERIC_TZ = 'jmv';

  /// NOT YET IMPLEMENTED.
  // TODO(https://github.com/dart-lang/intl/issues/74)
  static const String HOUR_MINUTE_TZ = 'jmz';

  /// NOT YET IMPLEMENTED.
  // TODO(https://github.com/dart-lang/intl/issues/74)
  static const String HOUR_GENERIC_TZ = 'jv';

  /// NOT YET IMPLEMENTED.
  // TODO(https://github.com/dart-lang/intl/issues/74)
  static const String HOUR_TZ = 'jz';
  static const String MINUTE = 'm';
  static const String MINUTE_SECOND = 'ms';
  static const String SECOND = 's';

  /// The locale in which we operate, e.g. 'en_US', or 'pt'.
  String _locale;

  /// The full template string. This may have been specified directly, or
  /// it may have been derived from a skeleton and the locale information
  /// on how to interpret that skeleton.
  String? _pattern;

  /// We parse the format string into individual [_DateFormatField] objects
  /// that are used to do the actual formatting and parsing. Do not use
  /// this variable directly, use the getter [_formatFields].
  List<_DateFormatField>? _formatFieldsPrivate;

  /// Getter for [_formatFieldsPrivate] that lazily initializes it.
  List<_DateFormatField> get _formatFields {
    if (_formatFieldsPrivate == null) {
      if (_pattern == null) _useDefaultPattern();
      _formatFieldsPrivate = parsePattern(_pattern!);
    }
    return _formatFieldsPrivate!;
  }

  /// We are being asked to do formatting without having set any pattern.
  /// Use a default.
  void _useDefaultPattern() {
    add_yMMMMd();
    add_jms();
  }

  /// A series of regular expressions used to parse a format string into its
  /// component fields.
  static final List<RegExp> _matchers = [
    // Quoted String - anything between single quotes, with escaping
    //   of single quotes by doubling them.
    // e.g. in the pattern 'hh 'o''clock'' will match 'o''clock'
    RegExp('^\'(?:[^\']|\'\')*\''),
    // Fields - any sequence of 1 or more of the same field characters.
    // e.g. in 'hh:mm:ss' will match hh, mm, and ss. But in 'hms' would
    // match each letter individually.
    RegExp('^(?:G+|y+|M+|k+|S+|E+|a+|h+|K+|H+|c+|L+|Q+|d+|D+|m+|s+|v+|z+|Z+)'),
    // Everything else - A sequence that is not quotes or field characters.
    // e.g. in 'hh:mm:ss' will match the colons.
    RegExp('^[^\'GyMkSEahKHcLQdDmsvzZ]+')
  ];

  /// Set our pattern, appending it to any existing patterns. Also adds a single
  /// space to separate the two.
  void _appendPattern(String inputPattern, [String separator = ' ']) {
    _pattern =
        _pattern == null ? inputPattern : '$_pattern$separator$inputPattern';
  }

  /// Add [inputPattern] to this instance as a pattern.
  ///
  /// If there was a previous pattern, then this appends to it, separating the
  /// two by [separator].  [inputPattern] is first looked up in our list of
  /// known skeletons.  If it's found there, then use the corresponding pattern
  /// for this locale.  If it's not, then treat [inputPattern] as an explicit
  /// pattern.
  DateFormat addPattern(String? inputPattern, [String separator = ' ']) {
    // TODO(alanknight): This is an expensive operation. Caching recently used
    // formats, or possibly introducing an entire 'locale' object that would
    // cache patterns for that locale could be a good optimization.
    // If we have already parsed the format fields, reset them.
    _formatFieldsPrivate = null;
    if (inputPattern == null) return this;
    if (!_availableSkeletons.containsKey(inputPattern)) {
      _appendPattern(inputPattern, separator);
    } else {
      _appendPattern(_availableSkeletons[inputPattern], separator);
    }
    return this;
  }

  /// Return the pattern that we use to format dates.
  String? get pattern => _pattern;

  /// Return the skeletons for our current locale.
  Map<dynamic, dynamic> get _availableSkeletons => dateTimePatterns[locale];

  /// Return the [DateSymbols] information for the locale.
  ///
  /// This can be useful to find lists like the names of weekdays or months in a
  /// locale, but the structure of this data may change, and it's generally
  /// better to go through the [format] and [parse] APIs.
  ///
  /// If the locale isn't present, or is uninitialized, throws.
  DateSymbols get dateSymbols {
    if (_locale != lastDateSymbolLocale) {
      lastDateSymbolLocale = _locale;
      cachedDateSymbols = dateTimeSymbols[_locale];
    }
    return cachedDateSymbols!;
  }

  static final Map<String, bool> _useNativeDigitsByDefault = {};

  /// Should a new DateFormat for [locale] have useNativeDigits true.
  ///
  /// For example, for locale 'ar' when this setting is true, DateFormat will
  /// format using Eastern Arabic digits, e.g. '\u0660, \u0661, \u0662'. If it
  /// is false, a new DateFormat will format using ASCII digits.
  static bool shouldUseNativeDigitsByDefaultFor(String locale) {
    return _useNativeDigitsByDefault[locale] ?? true;
  }

  /// Indicate if a new DateFormat for [locale] should have useNativeDigits
  /// true.
  ///
  /// For example, for locale 'ar' when this setting is true, DateFormat will
  /// format using Eastern Arabic digits, e.g. '\u0660, \u0661, \u0662'. If it
  /// is false, a new DateFormat will format using ASCII digits.
  ///
  /// If not indicated, the default value is true, so native digits will be
  /// used.
  static void useNativeDigitsByDefaultFor(String locale, bool value) {
    _useNativeDigitsByDefault[locale] = value;
  }

  bool? _useNativeDigits;

  /// Should we use native digits for printing DateTime, or ASCII.
  ///
  /// The default for this can be set using [useNativeDigitsByDefaultFor].
  bool get useNativeDigits => _useNativeDigits == null
      ? _useNativeDigits = shouldUseNativeDigitsByDefaultFor(locale)
      : _useNativeDigits!;

  /// Should we use native digits for printing DateTime, or ASCII.
  set useNativeDigits(bool native) {
    _useNativeDigits = native;
    // Invalidate any cached information that would depend on this setting.
    _digitMatcher = null;
    _localeZeroCodeUnit = null;
    _localeZero = null;
  }

  /// Caches digit matchers that we have already calculated for particular
  /// digits.
  ///
  /// Keys are the zero digits, and the values are matchers for digits in that
  /// locale.
  static final Map<String, RegExp> _digitMatchers = {};

  RegExp? _digitMatcher;

  /// A regular expression which matches against digits for this locale.
  RegExp get digitMatcher {
    if (_digitMatcher != null) return _digitMatcher!;
    _digitMatcher = _digitMatchers.putIfAbsent(localeZero, _initDigitMatcher);
    return _digitMatcher!;
  }

  int? _localeZeroCodeUnit;

  /// For performance, keep the code unit of the zero digit available.
  int get localeZeroCodeUnit => _localeZeroCodeUnit == null
      ? _localeZeroCodeUnit = localeZero.codeUnitAt(0)
      : _localeZeroCodeUnit!;

  String? _localeZero;

  /// For performance, keep the zero digit available.
  String get localeZero => _localeZero == null
      ? _localeZero = useNativeDigits ? dateSymbols.ZERODIGIT ?? '0' : '0'
      : _localeZero!;

  // Does this use non-ASCII digits, e.g. Eastern Arabic.
  bool get usesNativeDigits =>
      useNativeDigits && _localeZeroCodeUnit != constants.asciiZeroCodeUnit;

  /// Does this use ASCII digits
  bool get usesAsciiDigits => !usesNativeDigits;

  /// Given a numeric string in ASCII digits, return a copy updated for our
  /// locale digits.
  String _localizeDigits(String numberString) {
    if (usesAsciiDigits) return numberString;
    var newDigits = List<int>.filled(numberString.length, 0);
    var oldDigits = numberString.codeUnits;
    for (var i = 0; i < numberString.length; i++) {
      newDigits[i] =
          oldDigits[i] + localeZeroCodeUnit - constants.asciiZeroCodeUnit;
    }
    return String.fromCharCodes(newDigits);
  }

  /// A regular expression that matches for digits in a particular
  /// locale, defined by the digit for zero in that locale.
  RegExp _initDigitMatcher() {
    if (usesAsciiDigits) return regexp.asciiDigitMatcher;
    var localeDigits = Iterable.generate(10, (i) => i)
        .map((i) => localeZeroCodeUnit + i)
        .toList();
    var localeDigitsString = String.fromCharCodes(localeDigits);
    return RegExp('^[$localeDigitsString]+');
  }

  /// Return true if the locale exists, or if it is null. The null case
  /// is interpreted to mean that we use the default locale.
  static bool localeExists(String? localeName) {
    if (localeName == null) return false;
    return dateTimeSymbols.containsKey(localeName);
  }

  static List<_DateFormatField Function(String, DateFormat)>
      get _fieldConstructors => [
            (pattern, parent) => _DateFormatQuotedField(pattern, parent),
            (pattern, parent) => _DateFormatPatternField(pattern, parent),
            (pattern, parent) => _DateFormatLiteralField(pattern, parent)
          ];

  /// Parse the template pattern and return a list of field objects.
  @visibleForTesting
  @Deprecated('clients should not depend on this internal method')
  // ignore: library_private_types_in_public_api
  List<_DateFormatField> parsePattern(String pattern) {
    return _parsePatternHelper(pattern).reversed.toList();
  }

  /// Recursive helper for parsing the template pattern.
  List<_DateFormatField> _parsePatternHelper(String pattern) {
    if (pattern.isEmpty) return [];

    var matched = _match(pattern);
    if (matched == null) return [];

    var parsed =
        _parsePatternHelper(pattern.substring(matched.fullPattern().length));
    parsed.add(matched);
    return parsed;
  }

  /// Find elements in a string that are patterns for specific fields.
  _DateFormatField? _match(String pattern) {
    for (var i = 0; i < _matchers.length; i++) {
      var regex = _matchers[i];
      var match = regex.firstMatch(pattern);
      if (match != null) {
        return _fieldConstructors[i](match.group(0)!, this);
      }
    }
    return null;
  }
}

/// Defines a function type for creating DateTime instances.
typedef _DateTimeConstructor = DateTime Function(int year, int month, int day,
    int hour24, int minute, int second, int fractionalSecond, bool utc);
