Skip to content

Commit

Permalink
Merge pull request #11 from gbassisp/feature/support-intl-0.20
Browse files Browse the repository at this point in the history
deps: bump constraint on intl
  • Loading branch information
gbassisp authored Dec 18, 2024
2 parents f00c06e + dcf37a5 commit 623143a
Show file tree
Hide file tree
Showing 4 changed files with 96 additions and 4 deletions.
6 changes: 5 additions & 1 deletion analysis_options.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -2,4 +2,8 @@ include: package:very_good_analysis/analysis_options.yaml

analyzer:
exclude:
- example/*
- example/*

linter:
rules:
use_late_for_private_fields_and_variables: false
3 changes: 3 additions & 0 deletions lib/src/extensions.dart
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@ import 'package:any_date/any_date.dart';
import 'package:meta/meta.dart';

/// a collection of extensions on [DateTime]
@internal
extension DateTimeExtension on DateTime {
/// returns a [DateTime] as UTC after applying the offset
DateTime copyWithOffset(String offset) {
Expand Down Expand Up @@ -111,6 +112,8 @@ extension DateTimeExtension on DateTime {
allowRollover: true,
);
}

DateTime get dateOnly => DateTime(year, month, day);
}

const _parser = AnyDate();
Expand Down
37 changes: 34 additions & 3 deletions lib/src/param_cleanup_rules.dart
Original file line number Diff line number Diff line change
Expand Up @@ -84,7 +84,7 @@ const _knownSeparators = {..._usedSeparators, ..._specialSeparators};

/// these are the separators used by the default DateTime.parse
String _replaceSeparators(String formattedString, Iterable<String> separators) {
var result = formattedString;
var result = _replaceComma(formattedString);
result = replaceUtc(result);
final unknownSeparators = separators.toSet().difference(_knownSeparators);

Expand All @@ -97,6 +97,17 @@ String _replaceSeparators(String formattedString, Iterable<String> separators) {
return _restoreMillisecons(result, separator).replaceAll(separator, '-');
}

String _replaceComma(String formattedString) {
final re1 = RegExp(r',\s+');
final re2 = RegExp(r',\s+');
final re3 = RegExp(r'\s+');

return formattedString
.replaceAll(re1, ' ')
.replaceAll(re2, ' ')
.replaceAll(re3, ' ');
}

String _restoreMillisecons(String formattedString, String separator) {
// regex with T00:00:00-000
final r = RegExp(
Expand All @@ -111,9 +122,19 @@ String _restoreMillisecons(String formattedString, String separator) {
);
}

// .reversed because it works for disambiguation
// (e.g., in vi locale try 'thang 12' before 'thang 1')
Iterable<Month> _sortMonths(Iterable<Month> months) {
final sorted = months.toList()
..sort((a, b) => a.name.length.compareTo(b.name.length))
..sort((a, b) => a.number.compareTo(b.number));

return sorted.reversed;
}

Month? _expectMonth(DateParsingParameters parameters) {
final timestamp = parameters.formattedString.toLowerCase();
final month = parameters.parserInfo.months.where(
final month = _sortMonths(parameters.parserInfo.months).where(
(element) =>
element.name.tryToInt() == null &&
timestamp.contains(element.name.toLowerCase()),
Expand All @@ -125,12 +146,22 @@ Month? _expectMonth(DateParsingParameters parameters) {
return month.firstOrNullExtension ?? english.firstOrNullExtension;
}

// .reversed because it works for disambiguation
// (e.g., in vi locale try 'thang 12' before 'thang 1')
Iterable<Weekday> _sortWeekdays(Iterable<Weekday> weekdays) {
final sorted = weekdays.toList()
..sort((a, b) => a.name.length.compareTo(b.name.length))
..sort((a, b) => a.number.compareTo(b.number));

return sorted.reversed;
}

Weekday? _expectWeekday(DateParsingParameters parameters) {
// TODO(gbassisp): allow weekday in any part of the string
// currently unsupported because some locales can have a conflict between
// month and weekday (e.g., "Mar" in French for Mardi and Mars)
final timestamp = parameters.formattedString.toLowerCase();
var weekday = parameters.parserInfo.weekdays
var weekday = _sortWeekdays(parameters.parserInfo.weekdays)
.where(
(element) => timestamp.startsWith(element.name.toLowerCase()),
// (element) => timestamp
Expand Down
54 changes: 54 additions & 0 deletions test/failing_locales_test.dart
Original file line number Diff line number Diff line change
@@ -0,0 +1,54 @@
// the following locales are failing:
// vi
// nyn
// ln
// zh-TW
// zh_HK
// zh_CN
// zh
// ko
// mn
// ja
import 'package:any_date/any_date.dart';
import 'package:any_date/src/extensions.dart';
import 'package:intl/intl.dart';
import 'package:test/test.dart';

import 'test_values.dart';

const _failing = {
'vi',
'nyn',
'ln',
'zh_TW',
'zh_HK',
'zh_CN',
'zh',
'ko',
'mn',
'ja',
};
Future<void> main() async {
await initializeDateFormatting();

final date = DateTime.now().dateOnly;
group('ensure failing locales are working', () {
for (final l in _failing) {
final format = DateFormat.yMMMMd(l);
final formatted = format.format(date);
test('locale $l can parse $formatted text month', () {
final parser = AnyDate.fromLocale(l);

final parsed = parser.tryParse(formatted);

expect(parsed, equals(date));
});

test('sanity check - locale $l can self-parse $formatted text month', () {
final parsed = format.parse(formatted);

expect(parsed, equals(date));
});
}
});
}

0 comments on commit 623143a

Please sign in to comment.