Skip to content

Commit

Permalink
ready for 2.0.0-rc.1
Browse files Browse the repository at this point in the history
  • Loading branch information
kensnyder committed Nov 9, 2024
1 parent e38bd94 commit a5d3900
Show file tree
Hide file tree
Showing 12 changed files with 203 additions and 238 deletions.
198 changes: 25 additions & 173 deletions README.md
Original file line number Diff line number Diff line change
@@ -1,14 +1,14 @@
# any-date-parser

[![NPM Link](https://badgen.net/npm/v/any-date-parser?v=2.0.0)](https://npmjs.com/package/any-date-parser)
[![Language](https://badgen.net/static/language/TS?v=2.0.0)](https://github.com/search?q=repo:kensnyder/any-date-parser++language:TypeScript&type=code)
[![Build Status](https://github.com/kensnyder/any-date-parser/actions/workflows/workflow.yml/badge.svg?v=2.0.0)](https://github.com/kensnyder/any-date-parser/actions)
[![Code Coverage](https://codecov.io/gh/kensnyder/any-date-parser/branch/main/graph/badge.svg?v=2.0.0)](https://codecov.io/gh/kensnyder/any-date-parser)
![2000+ Tests](https://badgen.net/static/tests/2000+/green)
[![Gzipped Size](https://badgen.net/bundlephobia/minzip/any-date-parser?label=minzipped&v=2.0.0)](https://bundlephobia.com/package/any-date-parser@2.0.0)
[![Dependency details](https://badgen.net/bundlephobia/dependency-count/any-date-parser?v=2.0.0)](https://www.npmjs.com/package/any-date-parser?activeTab=dependencies)
[![Tree shakeable](https://badgen.net/bundlephobia/tree-shaking/any-date-parser?v=2.0.0)](https://www.npmjs.com/package/any-date-parser)
[![ISC License](https://badgen.net/github/license/kensnyder/any-date-parser?v=2.0.0)](https://opensource.org/licenses/ISC)
[![NPM Link](https://badgen.net/npm/v/any-date-parser?v=2.0.0-rc.1)](https://npmjs.com/package/any-date-parser)
[![Language](https://badgen.net/static/language/TS?v=2.0.0-rc.1)](https://github.com/search?q=repo:kensnyder/any-date-parser++language:TypeScript&type=code)
[![Build Status](https://github.com/kensnyder/any-date-parser/actions/workflows/workflow.yml/badge.svg?v=2.0.0-rc.1)](https://github.com/kensnyder/any-date-parser/actions)
[![Code Coverage](https://codecov.io/gh/kensnyder/any-date-parser/branch/main/graph/badge.svg?v=2.0.0-rc.1)](https://codecov.io/gh/kensnyder/any-date-parser)
![2400+ Tests](https://badgen.net/static/tests/2400+/green)
[![Gzipped Size](https://badgen.net/bundlephobia/minzip/any-date-parser?label=minzipped&v=2.0.0-rc.1)](https://bundlephobia.com/package/any-date-parser@2.0.0-rc.1)
[![Dependency details](https://badgen.net/bundlephobia/dependency-count/any-date-parser?v=2.0.0-rc.1)](https://www.npmjs.com/package/any-date-parser?activeTab=dependencies)
[![Tree shakeable](https://badgen.net/bundlephobia/tree-shaking/any-date-parser?v=2.0.0-rc.1)](https://www.npmjs.com/package/any-date-parser)
[![ISC License](https://badgen.net/github/license/kensnyder/any-date-parser?v=2.0.0-rc.1)](https://opensource.org/licenses/ISC)

The most comprehensive and accurate date parser for Node and browsers. It uses
`Intl` to provide parsing support for all installed locales.
Expand All @@ -20,7 +20,7 @@ The most comprehensive and accurate date parser for Node and browsers. It uses
OR

```html
<script src="https://cdn.jsdelivr.net/npm/any-date-parser@2.0.0/dist/browser-bundle.js"></script>
<script src="https://cdn.jsdelivr.net/npm/any-date-parser@2.0.0-rc.1/dist/browser-bundle.js"></script>
```

## Table of Contents
Expand All @@ -31,9 +31,6 @@ OR
1. [Supported formats](#supported-formats)
1. [Locale support](#locale-support)
1. [List of all supported locales](https://github.com/kensnyder/any-date-parser/blob/master/test-fixtures/localeList.ts)
1. [Adding custom formats](#adding-custom-formats)
1. [Removing parsing rules](#removing-parsing-rules)
1. [Creating a custom parser](#creating-a-custom-parser)
1. [Unit tests](#unit-tests)
1. [Contributing](#contributing)

Expand All @@ -48,6 +45,7 @@ OR
property, v2 will behave the same.
- If an input string does not match any known format, it will attempt a fuzzy
match, looking for date parts individually.
- Custom patterns are no longer supported

## Motivation

Expand Down Expand Up @@ -173,7 +171,6 @@ This means support for international formats such as:
- `es-MX` - `viernes, 27 de septiembre de 2024, 10:39:50 a.m. GMT-6`
- `bn-BD` - `শুক্রবার, ২৭ সেপ্টেম্বর, ২০২৪ এ ১০:৩৬:১০ AM GMT -৬`
- `el-GR` - `Παρασκευή 27 Σεπτεμβρίου 2024 στις 10:38:16 π.μ. GMT-6`
- `he-IL` - `יום שישי, 27 בספטמבר 2024 בשעה 10:38:53 GMT-6`
- `hi-IN` - `शुक्रवार, 27 सितंबर 2024 को 10:39:13 am GMT-6 बजे`
- `th-TH` - `วันศุกร์ที่ 27 กันยายน พ.ศ. 2567 เวลา 10 นาฬิกา 40 นาที 28 วินาที GMT-6`
- `ta-IN` - `வெள்ளி, 27 செப்டம்பர், 2024 அன்று 10:43:05 AM GMT-6`
Expand All @@ -195,151 +192,7 @@ Check out the
`-271821-04-20T00:00:00.000Z through +275760-09-13T00:00:00.000Z`.
- Only English timezone names are supported
- Does not support the Hijri calendar (`islamic-umalqura`)
- Does not support `ar` (Arabic) locales

## Adding custom formats

`any-date-parser` has an `addFormat()` function to add a custom parser.

First, parsers must have `matcher` or `template`.

- `matcher`: A RegExp to match a string
- `template`: A string with template variables such as `_YEAR_` `_MONTH_` etc.
that will be converted to a regular expression

Second, parsers must have `units` or `handler`.

- `units`: An array of unit strings to fit matches into (year, month, day, etc.)
- `handler`: A function that takes matches and returns an object with keys year,
month, day etc.

### Example 1: matcher + units

```ts
import parser, { Format } from 'any-date-parser';

parser.addFormat(
new Format({
matcher: /^(\d+) days? into month (\d+) in year (\d{4})$/,
units: ['day', 'month', 'year'],
})
);
```

Keep in mind that `\d` does not support other numbering system such as Chinese
or Bengali. To support those you can use the `template` option given in
[example 3](#example-3-template--units) and
[example 4](#example-4-template--handler).

### Example 2: matcher + handler

```ts
import parser, { Format } from 'any-date-parser';

parser.addFormat(
new Format({
matcher: /^(Q[1-4]) (\d{4})$/, // String such as "Q4 2004"
handler: function ([, quarter, year]) {
const monthByQuarter = { Q1: 1, Q2: 4, Q3: 7, Q4: 10 };
const month = monthByQuarter[quarter];
return { year, month };
},
})
);
```

### Example 3: template + units

```ts
import parser, { Format } from 'any-date-parser';

parser.addFormat(
new Format({
template: 'The (_DAY_)(?:_ORDINAL_) day of (_MONTH_), (_YEAR_)',
units: ['day', 'month', 'year'],
})
);
```

### Example 4: template + handler

```ts
import parser, { Format } from 'any-date-parser';

parser.addFormat(
new Format({
template: '^(Q[1-4]) (_YEAR_)$', // String such as "Q4 2004"
handler: function ([, quarter, year]) {
const monthByQuarter = { Q1: 1, Q2: 4, Q3: 7, Q4: 10 };
const month = monthByQuarter[quarter];
return { year, month };
},
})
);
```

### Removing parsing rules

To remove support for a certain format, use `removeFormat()`

```ts
import parser, { dayMonth, fuzzy } from 'any-date-parser';
import dayMonth from 'any-date-parser';

parser.removeFormat(dayMonth);
parser.removeFormat(fuzzy);
```

All exported formats:

- `time24Hours`
- `time12Hours`
- `yearMonthDayWithDots`
- `yearMonthDay`
- `dayMonthnameYear`
- `monthnameDayYear`
- `monthDayYear`
- `dayMonthYear`
- `chinese`
- `korean`
- `twitter`
- `today`
- `ago`
- `monthnameDay`
- `dayMonthname`
- `monthDay`
- `dayMonth`
- `yearMonthnameDay`
- `yearMonthDayWithSlashes`
- `atSeconds`
- `microsoftJson`
- `fuzzy`

### Creating a custom parser

To create a new parser with a limited list of formats or your own custom
formats, use `new Parser`

```ts
import { Parser, time24Hours, yearMonthDay, ago } from 'any-date-parser';

const myParser = new Parser();
myParser.addFormats([time24Hours, yearMonthDay, ago]);
```

Note that formats will be attempted in the order they were added.

You can convert your custom parser to a function. For example:

```ts
import { Parser, time24Hours, yearMonthDay, ago } from 'any-date-parser';
const myParser = new Parser();
// ....
myParser.addFormats(/*...*/);
// Pass locale if you want to override the detected default
Date.fromString = myParser.exportAsFunction();
Date.fromAny = myParser.exportAsFunctionAny();
```
- Does not support right-to-left script locales such as `ar` (Arabic) and `he` (Hebrew)

## Unit tests

Expand All @@ -360,23 +213,22 @@ incorporated.

24 hour time (any date format followed by a 24-hour time expression)

- 2020-10-06 17:41:28
- 2020-10-06T17:41:28Z
- 17:41:28
- 2020-10-06T17:41:28.999Z
- 2020-10-06T17:41:28.999999Z
- 2020-10-06T17:41:28.999999999Z
- 2020-10-06T17:41:28 MST
- 2020-10-06T17:41:28 Eastern Daylight Time
- 2020-10-06T17:41:28 GMT+03:00
- 2020-10-06T17:41:28 GMT-9
- 2020-10-06T17:41:28-09:00
- 2020-10-06T17:41:28+0900
- 17:41:28Z
- 17:41:28.999Z
- 17:41:28.999999Z
- 17:41:28.999999999Z
- 17:41:28 MST
- 17:41:28 Eastern Daylight Time
- 17:41:28 GMT+03:00
- 17:41:28 GMT-9
- 17:41:28-09:00
- 17:41:28+0900

12 hour time (any date format followed by a 12-hour time expression)

- March 14, 2015 at 9:26:53 am
- 14 Mar 2015 9:26:53 a.m.
- 9:26:53 am
- 9:26:53 a.m.
- 9:26:53am
- 9:26pm
- 9pm
Expand Down Expand Up @@ -451,7 +303,7 @@ day monthname
- 16 March
- 16 Mar

month day
month day (for locales: ee-TG en-AS,CA,FM,GH,GU,KE,MH,MP,US,VI,WS jp-JP sm-AS,SM)

- 03/14
- 03-14
Expand Down
2 changes: 1 addition & 1 deletion package.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"name": "any-date-parser",
"version": "1.6.0",
"version": "2.0.0-rc.1",
"description": "Parse a wide range of date formats including human-input dates",
"tags": [
"date",
Expand Down
3 changes: 2 additions & 1 deletion scripts/test.sh
Original file line number Diff line number Diff line change
Expand Up @@ -32,7 +32,8 @@ then
# make global luxon available to our specs
export NODE_PATH=$modulesPath
# set timezone to UTC and run tests
TZ=UTC npx vitest "$@"
export TZ=UTC
npx vitest "$@"
else
# Failed
echo "${RED}We failed to find the full-icu package path."
Expand Down
8 changes: 4 additions & 4 deletions src/PatternMatcher/getMatcher.ts
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ import LocaleHelper from '../LocaleHelper/LocaleHelper';
import { compile } from '../patterns/patterns';
import PatternMatcher from './PatternMatcher';

type HandlerResult = {
export type HandlerResult = {
year?: string | number;
month?: string | number;
monthname?: string;
Expand All @@ -18,7 +18,7 @@ type HandlerResult = {
invalid?: string;
};

type FinalResult = {
export type MatcherResult = {
year: number;
month: number;
day: number;
Expand All @@ -45,7 +45,7 @@ const matcherByLocale = {};
export default function getMatcher(locale: string) {
if (!matcherByLocale[locale]) {
const helper = LocaleHelper.factory(locale);
matcherByLocale[locale] = new PatternMatcher<HandlerResult, FinalResult>({
matcherByLocale[locale] = new PatternMatcher<HandlerResult, MatcherResult>({
doneChecker,
fallback: getFallback(locale),
patterns: compile(helper),
Expand Down Expand Up @@ -82,7 +82,7 @@ function getFallback(locale: string) {

function getFormatter(helper: LocaleHelper) {
return function format(extracted: HandlerResult) {
const result = {} as FinalResult;
const result = {} as MatcherResult;
for (const [name, value] of Object.entries(extracted)) {
if (name === 'monthname') {
if (value) {
Expand Down
8 changes: 4 additions & 4 deletions src/data/preprocessors.ts
Original file line number Diff line number Diff line change
Expand Up @@ -19,10 +19,10 @@ const preprocessors = {
],
he: [[/ב/gi, '']],
// "of" in various languages
de: [[/ um /g, '']],
pt: [[/de /gi, '']],
es: [[/de /gi, '']],
da: [[/den /gi, ''], ...periodsInsteadOfColons],
de: [[/ um /g, ' ']],
pt: [[/\sde /gi, ' ']],
es: [[/\sde /gi, ' ']],
da: [[/\sden /gi, ' '], ...periodsInsteadOfColons],
// Russian symbol after years
ru: [[/ г\./g, '']],
th: [
Expand Down
Loading

0 comments on commit a5d3900

Please sign in to comment.