From c775aa38de9e14633c93a9e4f2c957da71debeaa Mon Sep 17 00:00:00 2001 From: Morteza Ziyae Date: Fri, 8 Mar 2019 12:18:55 +0330 Subject: [PATCH] Add persian locale (fa-IR) for v2 --- src/esm/locale/index.js | 1 + src/format/index.js.flow | 3 +- src/index.js.flow | 6 +- src/locale/fa-IR/_lib/formatDistance/index.js | 91 ++++ src/locale/fa-IR/_lib/formatDistance/test.js | 219 ++++++++ src/locale/fa-IR/_lib/formatLong/index.js | 41 ++ src/locale/fa-IR/_lib/formatRelative/index.js | 12 + src/locale/fa-IR/_lib/localize/index.js | 169 ++++++ src/locale/fa-IR/_lib/match/index.js | 146 ++++++ src/locale/fa-IR/index.d.ts | 4 + src/locale/fa-IR/index.js | 27 + src/locale/fa-IR/index.js.flow | 33 ++ src/locale/fa-IR/test.js | 495 ++++++++++++++++++ src/locale/index.js | 1 + src/locale/index.js.flow | 1 + src/parse/index.js.flow | 3 +- typings.d.ts | 58 +- 17 files changed, 1300 insertions(+), 10 deletions(-) create mode 100644 src/locale/fa-IR/_lib/formatDistance/index.js create mode 100644 src/locale/fa-IR/_lib/formatDistance/test.js create mode 100644 src/locale/fa-IR/_lib/formatLong/index.js create mode 100644 src/locale/fa-IR/_lib/formatRelative/index.js create mode 100644 src/locale/fa-IR/_lib/localize/index.js create mode 100644 src/locale/fa-IR/_lib/match/index.js create mode 100644 src/locale/fa-IR/index.d.ts create mode 100644 src/locale/fa-IR/index.js create mode 100644 src/locale/fa-IR/index.js.flow create mode 100644 src/locale/fa-IR/test.js diff --git a/src/esm/locale/index.js b/src/esm/locale/index.js index fb4cbfee9f..9f58821f65 100644 --- a/src/esm/locale/index.js +++ b/src/esm/locale/index.js @@ -11,6 +11,7 @@ export { default as enUS } from './en-US/index.js' export { default as eo } from './eo/index.js' export { default as es } from './es/index.js' export { default as et } from './et/index.js' +export { default as faIR } from './fa-IR/index.js' export { default as fr } from './fr/index.js' export { default as gl } from './gl/index.js' export { default as he } from './he/index.js' diff --git a/src/format/index.js.flow b/src/format/index.js.flow index ffb52192de..8e82d898a3 100644 --- a/src/format/index.js.flow +++ b/src/format/index.js.flow @@ -42,6 +42,7 @@ declare module.exports: ( weekStartsOn?: 0 | 1 | 2 | 3 | 4 | 5 | 6, firstWeekContainsDate?: number, locale?: Locale, - awareOfUnicodeTokens?: boolean + useAdditionalWeekYearTokens?: boolean, + useAdditionalDayOfYearTokens?: boolean } ) => string diff --git a/src/index.js.flow b/src/index.js.flow index 06821f6aa7..91fd4380cd 100644 --- a/src/index.js.flow +++ b/src/index.js.flow @@ -224,7 +224,8 @@ declare module.exports: { weekStartsOn?: 0 | 1 | 2 | 3 | 4 | 5 | 6, firstWeekContainsDate?: number, locale?: Locale, - awareOfUnicodeTokens?: boolean + useAdditionalWeekYearTokens?: boolean, + useAdditionalDayOfYearTokens?: boolean } ) => string, @@ -437,7 +438,8 @@ declare module.exports: { locale?: Locale, weekStartsOn?: 0 | 1 | 2 | 3 | 4 | 5 | 6, firstWeekContainsDate?: 1 | 2 | 3 | 4 | 5 | 6 | 7, - awareOfUnicodeTokens?: boolean + useAdditionalWeekYearTokens?: boolean, + useAdditionalDayOfYearTokens?: boolean } ) => Date, diff --git a/src/locale/fa-IR/_lib/formatDistance/index.js b/src/locale/fa-IR/_lib/formatDistance/index.js new file mode 100644 index 0000000000..efbb5c3ed1 --- /dev/null +++ b/src/locale/fa-IR/_lib/formatDistance/index.js @@ -0,0 +1,91 @@ +var formatDistanceLocale = { + lessThanXSeconds: { + one: 'کمتر از یک ثانیه', + other: 'کمتر از {{count}} ثانیه' + }, + + xSeconds: { + one: '1 ثانیه', + other: '{{count}} ثانیه' + }, + + halfAMinute: 'نیم دقیقه', + + lessThanXMinutes: { + one: 'کمتر از یک دقیقه', + other: 'کمتر از {{count}} دقیقه' + }, + + xMinutes: { + one: '1 دقیقه', + other: '{{count}} دقیقه' + }, + + aboutXHours: { + one: 'حدود 1 ساعت', + other: 'حدود {{count}} ساعت' + }, + + xHours: { + one: '1 ساعت', + other: '{{count}} ساعت' + }, + + xDays: { + one: '1 روز', + other: '{{count}} روز' + }, + + aboutXMonths: { + one: 'حدود 1 ماه', + other: 'حدود {{count}} ماه' + }, + + xMonths: { + one: '1 ماه', + other: '{{count}} ماه' + }, + + aboutXYears: { + one: 'حدود 1 سال', + other: 'حدود {{count}} سال' + }, + + xYears: { + one: '1 سال', + other: '{{count}} سال' + }, + + overXYears: { + one: 'بیشتر از 1 سال', + other: 'بیشتر از {{count}} سال' + }, + + almostXYears: { + one: 'نزدیک 1 سال', + other: 'نزدیک {{count}} سال' + } +} + +export default function formatDistance(token, count, options) { + options = options || {} + + var result + if (typeof formatDistanceLocale[token] === 'string') { + result = formatDistanceLocale[token] + } else if (count === 1) { + result = formatDistanceLocale[token].one + } else { + result = formatDistanceLocale[token].other.replace('{{count}}', count) + } + + if (options.addSuffix) { + if (options.comparison > 0) { + return 'در ' + result + } else { + return result + ' قبل' + } + } + + return result +} diff --git a/src/locale/fa-IR/_lib/formatDistance/test.js b/src/locale/fa-IR/_lib/formatDistance/test.js new file mode 100644 index 0000000000..86d8c8ed35 --- /dev/null +++ b/src/locale/fa-IR/_lib/formatDistance/test.js @@ -0,0 +1,219 @@ +// @flow +/* eslint-env mocha */ + +import assert from 'power-assert' +import formatDistance from '.' + +describe('fa-IR locale > formatDistance', function() { + describe('lessThanXSeconds', function() { + context('when the count equals 1', function() { + it('returns a proper string', function() { + assert(formatDistance('lessThanXSeconds', 1) === 'کمتر از یک ثانیه') + }) + }) + + context('when the count is more than 1', function() { + it('returns a proper string', function() { + assert(formatDistance('lessThanXSeconds', 2) === 'کمتر از 2 ثانیه') + }) + }) + }) + + describe('xSeconds', function() { + context('when the count equals 1', function() { + it('returns a proper string', function() { + assert(formatDistance('xSeconds', 1) === '1 ثانیه') + }) + }) + + context('when the count is more than 1', function() { + it('returns a proper string', function() { + assert(formatDistance('xSeconds', 2) === '2 ثانیه') + }) + }) + }) + + describe('halfAMinute', function() { + it('returns a proper string', function() { + assert(formatDistance('halfAMinute') === 'نیم دقیقه') + }) + + it('ignores the second argument', function() { + assert(formatDistance('halfAMinute', 123) === 'نیم دقیقه') + }) + }) + + describe('lessThanXMinutes', function() { + context('when the count equals 1', function() { + it('returns a proper string', function() { + assert(formatDistance('lessThanXMinutes', 1) === 'کمتر از یک دقیقه') + }) + }) + + context('when the count is more than 1', function() { + it('returns a proper string', function() { + assert(formatDistance('lessThanXMinutes', 2) === 'کمتر از 2 دقیقه') + }) + }) + }) + + describe('xMinutes', function() { + context('when the count equals 1', function() { + it('returns a proper string', function() { + assert(formatDistance('xMinutes', 1) === '1 دقیقه') + }) + }) + + context('when the count is more than 1', function() { + it('returns a proper string', function() { + assert(formatDistance('xMinutes', 2) === '2 دقیقه') + }) + }) + }) + + describe('aboutXHours', function() { + context('when the count equals 1', function() { + it('returns a proper string', function() { + assert(formatDistance('aboutXHours', 1) === 'حدود 1 ساعت') + }) + }) + + context('when the count is more than 1', function() { + it('returns a proper string', function() { + assert(formatDistance('aboutXHours', 2) === 'حدود 2 ساعت') + }) + }) + }) + + describe('xHours', function() { + context('when the count equals 1', function() { + it('returns a proper string', function() { + assert(formatDistance('xHours', 1) === '1 ساعت') + }) + }) + + context('when the count is more than 1', function() { + it('returns a proper string', function() { + assert(formatDistance('xHours', 2) === '2 ساعت') + }) + }) + }) + + describe('xDays', function() { + context('when the count equals 1', function() { + it('returns a proper string', function() { + assert(formatDistance('xDays', 1) === '1 روز') + }) + }) + + context('when the count is more than 1', function() { + it('returns a proper string', function() { + assert(formatDistance('xDays', 2) === '2 روز') + }) + }) + }) + + describe('aboutXMonths', function() { + context('when the count equals 1', function() { + it('returns a proper string', function() { + assert(formatDistance('aboutXMonths', 1) === 'حدود 1 ماه') + }) + }) + + context('when the count is more than 1', function() { + it('returns a proper string', function() { + assert(formatDistance('aboutXMonths', 2) === 'حدود 2 ماه') + }) + }) + }) + + describe('xMonths', function() { + context('when the count equals 1', function() { + it('returns a proper string', function() { + assert(formatDistance('xMonths', 1) === '1 ماه') + }) + }) + + context('when the count is more than 1', function() { + it('returns a proper string', function() { + assert(formatDistance('xMonths', 2) === '2 ماه') + }) + }) + }) + + describe('aboutXYears', function() { + context('when the count equals 1', function() { + it('returns a proper string', function() { + assert(formatDistance('aboutXYears', 1) === 'حدود 1 سال') + }) + }) + + context('when the count is more than 1', function() { + it('returns a proper string', function() { + assert(formatDistance('aboutXYears', 2) === 'حدود 2 سال') + }) + }) + }) + + describe('xYears', function() { + context('when the count equals 1', function() { + it('returns a proper string', function() { + assert(formatDistance('xYears', 1) === '1 سال') + }) + }) + + context('when the count is more than 1', function() { + it('returns a proper string', function() { + assert(formatDistance('xYears', 2) === '2 سال') + }) + }) + }) + + describe('overXYears', function() { + context('when the count equals 1', function() { + it('returns a proper string', function() { + assert(formatDistance('overXYears', 1) === 'بیشتر از 1 سال') + }) + }) + + context('when the count is more than 1', function() { + it('returns a proper string', function() { + assert(formatDistance('overXYears', 2) === 'بیشتر از 2 سال') + }) + }) + }) + + describe('almostXYears', function() { + context('when the count equals 1', function() { + it('returns a proper string', function() { + assert(formatDistance('almostXYears', 1) === 'نزدیک 1 سال') + }) + }) + + context('when the count is more than 1', function() { + it('returns a proper string', function() { + assert(formatDistance('almostXYears', 2) === 'نزدیک 2 سال') + }) + }) + }) + + context('with a past suffix', function() { + it('adds `ago` to a string', function() { + var result = formatDistance('aboutXYears', 1, { + addSuffix: true, + comparison: -1 + }) + assert(result === 'حدود 1 سال قبل') + }) + }) + + context('with a future suffix', function() { + it('adds `in` to a string', function() { + var result = formatDistance('halfAMinute', null, { + addSuffix: true, + comparison: 1 + }) + assert(result === 'در نیم دقیقه') + }) + }) +}) diff --git a/src/locale/fa-IR/_lib/formatLong/index.js b/src/locale/fa-IR/_lib/formatLong/index.js new file mode 100644 index 0000000000..26dacf1ef6 --- /dev/null +++ b/src/locale/fa-IR/_lib/formatLong/index.js @@ -0,0 +1,41 @@ +import buildFormatLongFn from '../../../_lib/buildFormatLongFn/index.js' + +var dateFormats = { + full: 'EEEE do MMMM y', + long: 'do MMMM y', + medium: 'd MMM y', + short: 'yyyy/MM/dd' +} + +var timeFormats = { + full: 'h:mm:ss a zzzz', + long: 'h:mm:ss a z', + medium: 'h:mm:ss a', + short: 'h:mm a' +} + +var dateTimeFormats = { + full: "{{date}} 'در' {{time}}", + long: "{{date}} 'در' {{time}}", + medium: '{{date}}, {{time}}', + short: '{{date}}, {{time}}' +} + +var formatLong = { + date: buildFormatLongFn({ + formats: dateFormats, + defaultWidth: 'full' + }), + + time: buildFormatLongFn({ + formats: timeFormats, + defaultWidth: 'full' + }), + + dateTime: buildFormatLongFn({ + formats: dateTimeFormats, + defaultWidth: 'full' + }) +} + +export default formatLong diff --git a/src/locale/fa-IR/_lib/formatRelative/index.js b/src/locale/fa-IR/_lib/formatRelative/index.js new file mode 100644 index 0000000000..3bf556f161 --- /dev/null +++ b/src/locale/fa-IR/_lib/formatRelative/index.js @@ -0,0 +1,12 @@ +var formatRelativeLocale = { + lastWeek: "eeee 'گذشته در' p", + yesterday: "'دیروز در' p", + today: "'امروز در' p", + tomorrow: "'فردا در' p", + nextWeek: "eeee 'در' p", + other: 'P' +} + +export default function formatRelative(token, date, baseDate, options) { + return formatRelativeLocale[token] +} diff --git a/src/locale/fa-IR/_lib/localize/index.js b/src/locale/fa-IR/_lib/localize/index.js new file mode 100644 index 0000000000..f20af2bffb --- /dev/null +++ b/src/locale/fa-IR/_lib/localize/index.js @@ -0,0 +1,169 @@ +import buildLocalizeFn from '../../../_lib/buildLocalizeFn/index.js' + +var eraValues = { + narrow: ['ق', 'ب'], + abbreviated: ['ق.م.', 'ب.م.'], + wide: ['قبل از میلاد', 'بعد از میلاد'] +} + +var quarterValues = { + narrow: ['1', '2', '3', '4'], + abbreviated: ['س‌م1', 'س‌م2', 'س‌م3', 'س‌م4'], + wide: ['سه‌ماهه 1', 'سه‌ماهه 2', 'سه‌ماهه 3', 'سه‌ماهه 4'] +} + +// Note: in English, the names of days of the week and months are capitalized. +// If you are making a new locale based on this one, check if the same is true for the language you're working on. +// Generally, formatted dates should look like they are in the middle of a sentence, +// e.g. in Spanish language the weekdays and months should be in the lowercase. +var monthValues = { + narrow: ['ژ', 'ف', 'م', 'آ', 'م', 'ج', 'ج', 'آ', 'س', 'ا', 'ن', 'د'], + abbreviated: [ + 'ژانـ', + 'فور', + 'مارس', + 'آپر', + 'می', + 'جون', + 'جولـ', + 'آگو', + 'سپتـ', + 'اکتـ', + 'نوامـ', + 'دسامـ' + ], + wide: [ + 'ژانویه', + 'فوریه', + 'مارس', + 'آپریل', + 'می', + 'جون', + 'جولای', + 'آگوست', + 'سپتامبر', + 'اکتبر', + 'نوامبر', + 'دسامبر' + ] +} + +var dayValues = { + narrow: ['ی', 'د', 'س', 'چ', 'پ', 'ج', 'ش'], + short: ['1ش', '2ش', '3ش', '4ش', '5ش', 'ج', 'ش'], + abbreviated: [ + 'یکشنبه', + 'دوشنبه', + 'سه‌شنبه', + 'چهارشنبه', + 'پنجشنبه', + 'جمعه', + 'شنبه' + ], + wide: ['یکشنبه', 'دوشنبه', 'سه‌شنبه', 'چهارشنبه', 'پنجشنبه', 'جمعه', 'شنبه'] +} + +var dayPeriodValues = { + narrow: { + am: 'ق', + pm: 'ب', + midnight: 'ن', + noon: 'ظ', + morning: 'ص', + afternoon: 'ب.ظ.', + evening: 'ع', + night: 'ش' + }, + abbreviated: { + am: 'ق.ظ.', + pm: 'ب.ظ.', + midnight: 'نیمه‌شب', + noon: 'ظهر', + morning: 'صبح', + afternoon: 'بعدازظهر', + evening: 'عصر', + night: 'شب' + }, + wide: { + am: 'قبل‌ازظهر', + pm: 'بعدازظهر', + midnight: 'نیمه‌شب', + noon: 'ظهر', + morning: 'صبح', + afternoon: 'بعدازظهر', + evening: 'عصر', + night: 'شب' + } +} +var formattingDayPeriodValues = { + narrow: { + am: 'ق', + pm: 'ب', + midnight: 'ن', + noon: 'ظ', + morning: 'ص', + afternoon: 'ب.ظ.', + evening: 'ع', + night: 'ش' + }, + abbreviated: { + am: 'ق.ظ.', + pm: 'ب.ظ.', + midnight: 'نیمه‌شب', + noon: 'ظهر', + morning: 'صبح', + afternoon: 'بعدازظهر', + evening: 'عصر', + night: 'شب' + }, + wide: { + am: 'قبل‌ازظهر', + pm: 'بعدازظهر', + midnight: 'نیمه‌شب', + noon: 'ظهر', + morning: 'صبح', + afternoon: 'بعدازظهر', + evening: 'عصر', + night: 'شب' + } +} + +function ordinalNumber(dirtyNumber) { + return String(dirtyNumber) +} + +var localize = { + ordinalNumber: ordinalNumber, + + era: buildLocalizeFn({ + values: eraValues, + defaultWidth: 'wide' + }), + + quarter: buildLocalizeFn({ + values: quarterValues, + defaultWidth: 'wide', + argumentCallback: function(quarter) { + return Number(quarter) - 1 + } + }), + + month: buildLocalizeFn({ + values: monthValues, + defaultWidth: 'wide' + }), + + day: buildLocalizeFn({ + values: dayValues, + defaultWidth: 'wide' + }), + + dayPeriod: buildLocalizeFn({ + values: dayPeriodValues, + defaultWidth: 'wide', + formattingValues: formattingDayPeriodValues, + defaultFormattingWidth: 'wide' + }) +} + +export default localize diff --git a/src/locale/fa-IR/_lib/match/index.js b/src/locale/fa-IR/_lib/match/index.js new file mode 100644 index 0000000000..a09b44f60a --- /dev/null +++ b/src/locale/fa-IR/_lib/match/index.js @@ -0,0 +1,146 @@ +import buildMatchPatternFn from '../../../_lib/buildMatchPatternFn/index.js' +import buildMatchFn from '../../../_lib/buildMatchFn/index.js' + +var matchOrdinalNumberPattern = /^(\d+)(th|st|nd|rd)?/i +var parseOrdinalNumberPattern = /\d+/i + +var matchEraPatterns = { + narrow: /^(ق|ب)/i, + abbreviated: /^(ق\.?\s?م\.?|ق\.?\s?د\.?\s?م\.?|م\.?\s?|د\.?\s?م\.?)/i, + wide: /^(قبل از میلاد|قبل از دوران مشترک|میلادی|دوران مشترک|بعد از میلاد)/i +} +var parseEraPatterns = { + any: [/^قبل/i, /^بعد/i] +} + +var matchQuarterPatterns = { + narrow: /^[1234]/i, + abbreviated: /^س‌م[1234]/i, + wide: /^سه‌ماهه [1234]/i +} +var parseQuarterPatterns = { + any: [/1/i, /2/i, /3/i, /4/i] +} + +var matchMonthPatterns = { + narrow: /^[جژفمآاماسند]/i, + abbreviated: /^(جنو|ژانـ|ژانویه|فوریه|فور|مارس|آوریل|آپر|مه|می|ژوئن|جون|جول|جولـ|ژوئیه|اوت|آگو|سپتمبر|سپتامبر|اکتبر|اکتوبر|نوامبر|نوامـ|دسامبر|دسامـ|دسم)/i, + wide: /^(ژانویه|جنوری|فبروری|فوریه|مارچ|مارس|آپریل|اپریل|ایپریل|آوریل|مه|می|ژوئن|جون|جولای|ژوئیه|آگست|اگست|آگوست|اوت|سپتمبر|سپتامبر|اکتبر|اکتوبر|نوامبر|نومبر|دسامبر|دسمبر)/i +} +var parseMonthPatterns = { + narrow: [ + /^(ژ|ج)/i, + /^ف/i, + /^م/i, + /^(آ|ا)/i, + /^م/i, + /^(ژ|ج)/i, + /^(ج|ژ)/i, + /^(آ|ا)/i, + /^س/i, + /^ا/i, + /^ن/i, + /^د/i + ], + any: [ + /^ژا/i, + /^ف/i, + /^ما/i, + /^آپ/i, + /^(می|مه)/i, + /^(ژوئن|جون)/i, + /^(ژوئی|جول)/i, + /^(اوت|آگ)/i, + /^س/i, + /^(اوک|اک)/i, + /^ن/i, + /^د/i + ] +} + +var matchDayPatterns = { + narrow: /^[شیدسچپج]/i, + short: /^(ش|ج|1ش|2ش|3ش|4ش|5ش)/i, + abbreviated: /^(یکشنبه|دوشنبه|سه‌شنبه|چهارشنبه|پنج‌شنبه|جمعه|شنبه)/i, + wide: /^(یکشنبه|دوشنبه|سه‌شنبه|چهارشنبه|پنج‌شنبه|جمعه|شنبه)/i +} +var parseDayPatterns = { + narrow: [/^ی/i, /^دو/i, /^س/i, /^چ/i, /^پ/i, /^ج/i, /^ش/i], + any: [ + /^(ی|1ش|یکشنبه)/i, + /^(د|2ش|دوشنبه)/i, + /^(س|3ش|سه‌شنبه)/i, + /^(چ|4ش|چهارشنبه)/i, + /^(پ|5ش|پنجشنبه)/i, + /^(ج|جمعه)/i, + /^(ش|شنبه)/i + ] +} + +var matchDayPeriodPatterns = { + narrow: /^(ب|ق|ن|ظ|ص|ب.ظ.|ع|ش)/i, + abbreviated: /^(ق.ظ.|ب.ظ.|نیمه‌شب|ظهر|صبح|بعدازظهر|عصر|شب)/i, + wide: /^(قبل‌ازظهر|نیمه‌شب|ظهر|صبح|بعدازظهر|عصر|شب)/i +} +var parseDayPeriodPatterns = { + any: { + am: /^(ق|ق.ظ.|قبل‌ازظهر)/i, + pm: /^(ب|ب.ظ.|بعدازظهر)/i, + midnight: /^(‌نیمه‌شب|ن)/i, + noon: /^(ظ|ظهر)/i, + morning: /(ص|صبح)/i, + afternoon: /(ب|ب.ظ.|بعدازظهر)/i, + evening: /(ع|عصر)/i, + night: /(ش|شب)/i + } +} + +var match = { + ordinalNumber: buildMatchPatternFn({ + matchPattern: matchOrdinalNumberPattern, + parsePattern: parseOrdinalNumberPattern, + valueCallback: function(value) { + return parseInt(value, 10) + } + }), + + era: buildMatchFn({ + matchPatterns: matchEraPatterns, + defaultMatchWidth: 'wide', + parsePatterns: parseEraPatterns, + defaultParseWidth: 'any' + }), + + quarter: buildMatchFn({ + matchPatterns: matchQuarterPatterns, + defaultMatchWidth: 'wide', + parsePatterns: parseQuarterPatterns, + defaultParseWidth: 'any', + valueCallback: function(index) { + return index + 1 + } + }), + + month: buildMatchFn({ + matchPatterns: matchMonthPatterns, + defaultMatchWidth: 'wide', + parsePatterns: parseMonthPatterns, + defaultParseWidth: 'any' + }), + + day: buildMatchFn({ + matchPatterns: matchDayPatterns, + defaultMatchWidth: 'wide', + parsePatterns: parseDayPatterns, + defaultParseWidth: 'any' + }), + + dayPeriod: buildMatchFn({ + matchPatterns: matchDayPeriodPatterns, + defaultMatchWidth: 'any', + parsePatterns: parseDayPeriodPatterns, + defaultParseWidth: 'any' + }) +} + +export default match diff --git a/src/locale/fa-IR/index.d.ts b/src/locale/fa-IR/index.d.ts new file mode 100644 index 0000000000..5f2f9138ad --- /dev/null +++ b/src/locale/fa-IR/index.d.ts @@ -0,0 +1,4 @@ +// This file is generated automatically by `scripts/build/typings.js`. Please, don't change it. + +import { faIR } from 'date-fns/locale' +export = faIR diff --git a/src/locale/fa-IR/index.js b/src/locale/fa-IR/index.js new file mode 100644 index 0000000000..9fe9d06041 --- /dev/null +++ b/src/locale/fa-IR/index.js @@ -0,0 +1,27 @@ +import formatDistance from './_lib/formatDistance/index.js' +import formatLong from './_lib/formatLong/index.js' +import formatRelative from './_lib/formatRelative/index.js' +import localize from './_lib/localize/index.js' +import match from './_lib/match/index.js' + +/** + * @type {Locale} + * @category Locales + * @summary Persian/Farsi locale (Iran). + * @language Persian + * @iso-639-2 ira + * @author Morteza Ziyae [@mort3za]{@link https://github.com/mort3za} + */ +var locale = { + formatDistance: formatDistance, + formatLong: formatLong, + formatRelative: formatRelative, + localize: localize, + match: match, + options: { + weekStartsOn: 0 /* Sunday */, + firstWeekContainsDate: 1 + } +} + +export default locale diff --git a/src/locale/fa-IR/index.js.flow b/src/locale/fa-IR/index.js.flow new file mode 100644 index 0000000000..1fb5c2c1c0 --- /dev/null +++ b/src/locale/fa-IR/index.js.flow @@ -0,0 +1,33 @@ +// @flow +// This file is generated automatically by `scripts/build/typings.js`. Please, don't change it. + +type Locale = { + formatDistance: Function, + formatRelative: Function, + localize: { + ordinalNumber: Function, + era: Function, + quarter: Function, + month: Function, + day: Function, + dayPeriod: Function + }, + formatLong: Object, + date: Function, + time: Function, + dateTime: Function, + match: { + ordinalNumber: Function, + era: Function, + quarter: Function, + month: Function, + day: Function, + dayPeriod: Function + }, + options?: { + weekStartsOn?: 0 | 1 | 2 | 3 | 4 | 5 | 6, + firstWeekContainsDate?: 1 | 2 | 3 | 4 | 5 | 6 | 7 + } +} + +declare module.exports: Locale diff --git a/src/locale/fa-IR/test.js b/src/locale/fa-IR/test.js new file mode 100644 index 0000000000..325242cf25 --- /dev/null +++ b/src/locale/fa-IR/test.js @@ -0,0 +1,495 @@ +// @flow +/* eslint-env mocha */ + +import assert from 'power-assert' +import locale from '.' + +import format from '../../format' +import formatDistance from '../../formatDistance' +import formatDistanceStrict from '../../formatDistanceStrict' +import formatRelative from '../../formatRelative' +import parse from '../../parse' + +describe('fa-IR locale', function() { + context('with `format`', function() { + var date = new Date(1986, 3 /* Apr */, 5, 10, 32, 0, 900) + + it('era', function() { + var result = format(date, 'G, GGGG, GGGGG', { locale: locale }) + assert(result === 'ب.م., بعد از میلاد, ب') + }) + + describe('year', function() { + it('ordinal regular year', function() { + var result = format(date, "'سال' yo", { locale: locale }) + assert(result === 'سال 1986') + }) + + it('ordinal local week-numbering year', function() { + var result = format(date, "'سال شماره' Yo", { locale: locale }) + assert(result === 'سال شماره 1986') + }) + }) + + describe('quarter', function() { + it('formatting quarter', function() { + var result = format(date, "'سه‌ماهه' Qo, QQQ, QQQQ, QQQQQ", { + locale: locale + }) + assert(result === 'سه‌ماهه 2, س‌م2, سه‌ماهه 2, 2') + }) + + it('stand-alone quarter', function() { + var result = format(date, "'سه‌ماهه' qo, qqq, qqqq, qqqqq", { + locale: locale + }) + assert(result === 'سه‌ماهه 2, س‌م2, سه‌ماهه 2, 2') + }) + }) + + describe('month', function() { + it('formatting month', function() { + var result = format(date, 'do MMMM', { locale: locale }) + assert(result === '5 آپریل') + }) + + it('stand-alone month', function() { + var result = format(date, "'ماه' Lo, LLL, LLLL, LLLLL", { + locale: locale + }) + assert(result === 'ماه 4, آپر, آپریل, آ') + }) + }) + + describe('week', function() { + it('ordinal local week of year', function() { + var date = new Date(1986, 3 /* Apr */, 6) + var result = format(date, "'هفته' wo", { locale: locale }) + assert(result === 'هفته 15') + }) + + it('ordinal ISO week of year', function() { + var date = new Date(1986, 3 /* Apr */, 6) + var result = format(date, "'هفته ایزو' Io", { locale: locale }) + assert(result === 'هفته ایزو 14') + }) + }) + + describe('day', function() { + it('ordinal date', function() { + var result = format(date, "'امروز' do 'است'", { locale: locale }) + assert(result === 'امروز 5 است') + }) + + it('ordinal day of year', function() { + var result = format(date, "'روز' Do 'از سال'", { locale: locale }) + assert(result === 'روز 95 از سال') + }) + }) + + describe('week day', function() { + it('day of week', function() { + var result = format(date, 'E, EEEE, EEEEE, EEEEEE', { locale: locale }) + assert(result === 'شنبه, شنبه, ش, ش') + }) + + it('ordinal day of week', function() { + var result = format(date, "'روز' eo 'از هفته'", { locale: locale }) + assert(result === 'روز 7 از هفته') + }) + }) + + describe('day period and hour', function() { + it('ordinal hour', function() { + var result = format(date, "'ساعت' ho", { locale: locale }) + assert(result === 'ساعت 10') + }) + + it('AM, PM', function() { + var result = format(date, 'h a, h aaaa, haaaaa', { locale: locale }) + assert(result === '10 ق.ظ., 10 قبل‌ازظهر, 10ق') + }) + + it('AM, PM, noon, midnight', function() { + var result = format( + new Date(1986, 3 /* Apr */, 6, 0), + 'b, bbbb, bbbbb', + { locale: locale } + ) + assert(result === 'نیمه‌شب, نیمه‌شب, ن') + }) + + it('flexible day periods', function() { + it('works as expected', function() { + var result = format(date, 'h B', { locale: locale }) + assert(result === '10 صبح') + }) + }) + }) + + it('ordinal minute', function() { + var result = format(date, "'دقیقه' mo", { locale: locale }) + assert(result === 'دقیقه 32') + }) + + it('ordinal second', function() { + var result = format(date, "'ثانیه' so", { locale: locale }) + assert(result === 'ثانیه 0') + }) + + describe('long format', function() { + it('short date', function() { + var result = format(date, 'P', { locale: locale }) + assert(result === '1986/04/05') + }) + + it('medium date', function() { + var result = format(date, 'PP', { locale: locale }) + assert(result === '5 آپر 1986') + }) + + it('long date', function() { + var result = format(date, 'PPP', { locale: locale }) + assert(result === '5 آپریل 1986') + }) + + it('full date', function() { + var result = format(date, 'PPPP', { locale: locale }) + assert(result === 'شنبه 5 آپریل 1986') + }) + + it('short time', function() { + var result = format(date, 'p', { locale: locale }) + assert(result === '10:32 ق.ظ.') + }) + + it('medium time', function() { + var result = format(date, 'pp', { locale: locale }) + assert(result === '10:32:00 ق.ظ.') + }) + + it('short date + time', function() { + var result = format(date, 'Pp', { locale: locale }) + assert(result === '1986/04/05, 10:32 ق.ظ.') + }) + + it('medium date + time', function() { + var result = format(date, 'PPpp', { locale: locale }) + assert(result === '5 آپر 1986, 10:32:00 ق.ظ.') + }) + + it('long date + time', function() { + var result = format(date, 'PPPp', { locale: locale }) + assert(result === '5 آپریل 1986 در 10:32 ق.ظ.') + }) + + it('full date + time', function() { + var result = format(date, 'PPPPp', { locale: locale }) + assert(result === 'شنبه 5 آپریل 1986 در 10:32 ق.ظ.') + }) + }) + }) + + context('with `formatDistance`', function() { + it('works as expected', function() { + var result = formatDistance( + new Date(1986, 3, 4, 10, 32, 25), + new Date(1986, 3, 4, 10, 32, 0), + { locale: locale, includeSeconds: true } + ) + assert(result === 'نیم دقیقه') + }) + + context('when `addSuffix` option is true', function() { + it('adds a future suffix', function() { + var result = formatDistance( + new Date(1986, 3, 4, 10, 32, 7), + new Date(1986, 3, 4, 10, 32, 0), + { locale: locale, includeSeconds: true, addSuffix: true } + ) + assert(result === 'در کمتر از 10 ثانیه') + }) + + it('adds a past suffix', function() { + var result = formatDistance( + new Date(1986, 3, 4, 10, 32, 0), + new Date(1986, 3, 4, 11, 32, 0), + { locale: locale, addSuffix: true } + ) + assert(result === 'حدود 1 ساعت قبل') + }) + }) + }) + + context('with `formatDistanceStrict`', function() { + it('works as expected', function() { + var result = formatDistanceStrict( + new Date(1986, 3, 4, 10, 32, 0), + new Date(1986, 3, 4, 12, 32, 0), + { locale: locale, unit: 'minute' } + ) + assert(result === '120 دقیقه') + }) + + describe('when `addSuffix` option is true', function() { + it('adds a future suffix', function() { + var result = formatDistanceStrict( + new Date(1986, 3, 4, 10, 32, 25), + new Date(1986, 3, 4, 10, 32, 0), + { locale: locale, addSuffix: true } + ) + assert(result === 'در 25 ثانیه') + }) + + it('adds a past suffix', function() { + var result = formatDistanceStrict( + new Date(1986, 3, 4, 10, 32, 0), + new Date(1986, 3, 4, 11, 32, 0), + { locale: locale, addSuffix: true } + ) + assert(result === '1 ساعت قبل') + }) + }) + }) + + context('with `formatRelative`', function() { + var baseDate = new Date(1986, 3 /* Apr */, 4, 10, 32, 0, 900) + + it('last week', function() { + var result = formatRelative(new Date(1986, 3 /* Apr */, 1), baseDate, { + locale: locale + }) + assert(result === 'سه‌شنبه گذشته در 12:00 ق.ظ.') + }) + + it('yesterday', function() { + var result = formatRelative( + new Date(1986, 3 /* Apr */, 3, 22, 22), + baseDate, + { locale: locale } + ) + assert(result === 'دیروز در 10:22 ب.ظ.') + }) + + it('today', function() { + var result = formatRelative( + new Date(1986, 3 /* Apr */, 4, 16, 50), + baseDate, + { locale: locale } + ) + assert(result === 'امروز در 4:50 ب.ظ.') + }) + + it('tomorrow', function() { + var result = formatRelative( + new Date(1986, 3 /* Apr */, 5, 7, 30), + baseDate, + { locale: locale } + ) + assert(result === 'فردا در 7:30 ق.ظ.') + }) + + it('next week', function() { + var result = formatRelative( + new Date(1986, 3 /* Apr */, 6, 12, 0), + baseDate, + { locale: locale } + ) + assert(result === 'یکشنبه در 12:00 ب.ظ.') + }) + + it('after the next week', function() { + var result = formatRelative( + new Date(1986, 3 /* Apr */, 11, 16, 50), + baseDate, + { locale: locale } + ) + assert(result === '1986/04/11') + }) + }) + + context('with `parse`', function() { + var baseDate = new Date(1986, 3 /* Apr */, 4, 10, 32, 0, 900) + + describe('era', function() { + it('abbreviated', function() { + var result = parse('10000 ق.م.', 'yyyyy G', baseDate, { + locale: locale + }) + assert.deepEqual(result, new Date(-9999, 0 /* Jan */, 1)) + }) + + it('wide', function() { + var result = parse('2018 بعد از میلاد', 'yyyy GGGG', baseDate, { + locale: locale + }) + assert.deepEqual(result, new Date(2018, 0 /* Jan */, 1)) + }) + + it('narrow', function() { + var result = parse('44 ق', 'y GGGGG', baseDate, { locale: locale }) + assert.deepEqual(result, new Date(-43, 0 /* Jan */, 1)) + }) + }) + + it('ordinal year', function() { + var result = parse('2017th', 'yo', baseDate, { locale: locale }) + assert.deepEqual(result, new Date(2017, 0 /* Jan */, 1)) + }) + + describe('quarter', function() { + it('ordinal', function() { + var result = parse('1st', 'Qo', baseDate, { locale: locale }) + assert.deepEqual(result, new Date(1986, 0 /* Jan */, 1)) + }) + + it('abbreviated', function() { + var result = parse('س‌م3', 'QQQ', baseDate, { locale: locale }) + assert.deepEqual(result, new Date(1986, 6 /* Jul */, 1)) + }) + + it('wide', function() { + var result = parse('سه‌ماهه 4', 'QQQQ', baseDate, { + locale: locale + }) + assert.deepEqual(result, new Date(1986, 9 /* Oct */, 1)) + }) + + it('narrow', function() { + var result = parse('1', 'QQQQQ', baseDate, { locale: locale }) + assert.deepEqual(result, new Date(1986, 0 /* Jan */, 1)) + }) + }) + + describe('month', function() { + it('ordinal', function() { + var result = parse('6th', 'Mo', baseDate, { locale: locale }) + assert.deepEqual(result, new Date(1986, 5 /* Jun */, 1)) + }) + + it('abbreviated', function() { + var result = parse('نوامـ', 'MMM', baseDate, { locale: locale }) + assert.deepEqual(result, new Date(1986, 10 /* Nov */, 1)) + }) + + it('wide', function() { + var result = parse('فوریه', 'MMMM', baseDate, { locale: locale }) + assert.deepEqual(result, new Date(1986, 1 /* Feb */, 1)) + }) + + it('narrow', function() { + var result = parse('ژ', 'MMMMM', baseDate, { locale: locale }) + assert.deepEqual(result, new Date(1986, 0 /* Jan */, 1)) + }) + }) + + it('ordinal week of year', function() { + var result = parse('49', 'wo', baseDate, { locale: locale }) + assert.deepEqual(result, new Date(1986, 10 /* Nov */, 30)) + }) + + it('ordinal day of month', function() { + var result = parse('28', 'do', baseDate, { locale: locale }) + assert.deepEqual(result, new Date(1986, 3 /* Apr */, 28)) + }) + + it('ordinal day of year', function() { + var result = parse('200', 'Do', baseDate, { locale: locale }) + assert.deepEqual(result, new Date(1986, 6 /* Jul */, 19)) + }) + + describe('day of week', function() { + it('abbreviated', function() { + var result = parse('2ش', 'E', baseDate, { locale: locale }) + assert.deepEqual(result, new Date(1986, 2 /* Mar */, 31)) + }) + + it('wide', function() { + var result = parse('سه‌شنبه', 'EEEE', baseDate, { locale: locale }) + assert.deepEqual(result, new Date(1986, 3 /* Apr */, 1)) + }) + + it('narrow', function() { + var result = parse('چ', 'EEEEE', baseDate, { locale: locale }) + assert.deepEqual(result, new Date(1986, 3 /* Apr */, 2)) + }) + + it('short', function() { + var result = parse('پ', 'EEEEEE', baseDate, { locale: locale }) + assert.deepEqual(result, new Date(1986, 3 /* Apr */, 3)) + }) + }) + + it('ordinal local day of week', function() { + var result = parse( + '2nd day of the week', + "eo 'day of the week'", + baseDate, + { locale: locale } + ) + assert.deepEqual(result, new Date(1986, 2 /* Mar */, 31)) + }) + + describe('AM, PM', function() { + it('abbreviated', function() { + var result = parse('5 ق.ظ.', 'h a', baseDate, { locale: locale }) + assert.deepEqual(result, new Date(1986, 3 /* Apr */, 4, 5)) + }) + + it('wide', function() { + var result = parse('5 بعدازظهر', 'h aaaa', baseDate, { locale: locale }) + assert.deepEqual(result, new Date(1986, 3 /* Apr */, 4, 17)) + }) + + it('narrow', function() { + var result = parse('11 ق', 'h aaaaa', baseDate, { locale: locale }) + assert.deepEqual(result, new Date(1986, 3 /* Apr */, 4, 11)) + }) + }) + + describe('AM, PM, noon, midnight', function() { + it('abbreviated', function() { + var result = parse('ظهر', 'b', baseDate, { locale: locale }) + assert.deepEqual(result, new Date(1986, 3 /* Apr */, 4, 12)) + }) + + it('wide', function() { + var result = parse('نیمه‌شب', 'bbbb', baseDate, { locale: locale }) + assert.deepEqual(result, new Date(1986, 3 /* Apr */, 4, 0)) + }) + + it('narrow', function() { + var result = parse('ن', 'bbbbb', baseDate, { locale: locale }) + assert.deepEqual(result, new Date(1986, 3 /* Apr */, 4, 0)) + }) + }) + + describe('flexible day period', function() { + it('abbreviated', function() { + var result = parse('2 نیمه‌شب', 'h B', baseDate, { locale: locale }) + assert.deepEqual(result, new Date(1986, 3 /* Apr */, 4, 2)) + }) + + it('wide', function() { + var result = parse('12 بعدازظهر', 'h BBBB', baseDate, { + locale: locale + }) + assert.deepEqual(result, new Date(1986, 3 /* Apr */, 4, 12)) + }) + + it('narrow', function() { + var result = parse('5 ع', 'h BBBBB', baseDate, { + locale: locale + }) + assert.deepEqual(result, new Date(1986, 3 /* Apr */, 4, 17)) + }) + }) + + it('ordinal time', function() { + var dateString = '1st hour, 2nd minute, 3rd second' + var formatString = "ho 'hour', mo 'minute', so 'second'" + var result = parse(dateString, formatString, baseDate, { locale: locale }) + assert.deepEqual(result, new Date(1986, 3 /* Apr */, 4, 1, 2, 3)) + }) + }) +}) diff --git a/src/locale/index.js b/src/locale/index.js index 2a42546296..7cf30533c0 100644 --- a/src/locale/index.js +++ b/src/locale/index.js @@ -12,6 +12,7 @@ module.exports = { eo: require('./eo/index.js'), es: require('./es/index.js'), et: require('./et/index.js'), + faIR: require('./fa-IR/index.js'), fr: require('./fr/index.js'), gl: require('./gl/index.js'), he: require('./he/index.js'), diff --git a/src/locale/index.js.flow b/src/locale/index.js.flow index fa9ac6f606..40f85eecd8 100644 --- a/src/locale/index.js.flow +++ b/src/locale/index.js.flow @@ -49,6 +49,7 @@ declare module.exports: { eo: Locale, es: Locale, et: Locale, + faIR: Locale, fi: Locale, fil: Locale, fr: Locale, diff --git a/src/parse/index.js.flow b/src/parse/index.js.flow index bb73bf9fe0..40e740d2da 100644 --- a/src/parse/index.js.flow +++ b/src/parse/index.js.flow @@ -43,6 +43,7 @@ declare module.exports: ( locale?: Locale, weekStartsOn?: 0 | 1 | 2 | 3 | 4 | 5 | 6, firstWeekContainsDate?: 1 | 2 | 3 | 4 | 5 | 6 | 7, - awareOfUnicodeTokens?: boolean + useAdditionalWeekYearTokens?: boolean, + useAdditionalDayOfYearTokens?: boolean } ) => Date diff --git a/typings.d.ts b/typings.d.ts index 65f2d8b21d..03204aae09 100644 --- a/typings.d.ts +++ b/typings.d.ts @@ -408,7 +408,8 @@ declare module 'date-fns' { weekStartsOn?: 0 | 1 | 2 | 3 | 4 | 5 | 6 firstWeekContainsDate?: number locale?: Locale - awareOfUnicodeTokens?: boolean + useAdditionalWeekYearTokens?: boolean + useAdditionalDayOfYearTokens?: boolean } ): string namespace format { @@ -840,7 +841,8 @@ declare module 'date-fns' { locale?: Locale weekStartsOn?: 0 | 1 | 2 | 3 | 4 | 5 | 6 firstWeekContainsDate?: 1 | 2 | 3 | 4 | 5 | 6 | 7 - awareOfUnicodeTokens?: boolean + useAdditionalWeekYearTokens?: boolean + useAdditionalDayOfYearTokens?: boolean } ): Date namespace parse { @@ -7409,7 +7411,8 @@ declare module 'date-fns/esm' { weekStartsOn?: 0 | 1 | 2 | 3 | 4 | 5 | 6 firstWeekContainsDate?: number locale?: Locale - awareOfUnicodeTokens?: boolean + useAdditionalWeekYearTokens?: boolean + useAdditionalDayOfYearTokens?: boolean } ): string namespace format { @@ -7841,7 +7844,8 @@ declare module 'date-fns/esm' { locale?: Locale weekStartsOn?: 0 | 1 | 2 | 3 | 4 | 5 | 6 firstWeekContainsDate?: 1 | 2 | 3 | 4 | 5 | 6 | 7 - awareOfUnicodeTokens?: boolean + useAdditionalWeekYearTokens?: boolean + useAdditionalDayOfYearTokens?: boolean } ): Date namespace parse { @@ -14165,6 +14169,11 @@ declare module 'date-fns/locale' { } + const faIR: Locale + namespace faIR { + + } + const fi: Locale namespace fi { @@ -14431,6 +14440,11 @@ declare module 'date-fns/locale/et' { export = et } +declare module 'date-fns/locale/fa-IR' { + import { faIR } from 'date-fns/locale' + export = faIR +} + declare module 'date-fns/locale/fi' { import { fi } from 'date-fns/locale' export = fi @@ -14696,6 +14710,11 @@ declare module 'date-fns/locale/et/index' { export = et } +declare module 'date-fns/locale/fa-IR/index' { + import { faIR } from 'date-fns/locale' + export = faIR +} + declare module 'date-fns/locale/fi/index' { import { fi } from 'date-fns/locale' export = fi @@ -14961,6 +14980,11 @@ declare module 'date-fns/locale/et/index.js' { export = et } +declare module 'date-fns/locale/fa-IR/index.js' { + import { faIR } from 'date-fns/locale' + export = faIR +} + declare module 'date-fns/locale/fi/index.js' { import { fi } from 'date-fns/locale' export = fi @@ -15229,6 +15253,11 @@ declare module 'date-fns/esm/locale' { } + const faIR: Locale + namespace faIR { + + } + const fi: Locale namespace fi { @@ -15495,6 +15524,11 @@ declare module 'date-fns/esm/locale/et' { export default et } +declare module 'date-fns/esm/locale/fa-IR' { + import { faIR } from 'date-fns/esm/locale' + export default faIR +} + declare module 'date-fns/esm/locale/fi' { import { fi } from 'date-fns/esm/locale' export default fi @@ -15760,6 +15794,11 @@ declare module 'date-fns/esm/locale/et/index' { export default et } +declare module 'date-fns/esm/locale/fa-IR/index' { + import { faIR } from 'date-fns/esm/locale' + export default faIR +} + declare module 'date-fns/esm/locale/fi/index' { import { fi } from 'date-fns/esm/locale' export default fi @@ -16025,6 +16064,11 @@ declare module 'date-fns/esm/locale/et/index.js' { export default et } +declare module 'date-fns/esm/locale/fa-IR/index.js' { + import { faIR } from 'date-fns/esm/locale' + export default faIR +} + declare module 'date-fns/esm/locale/fi/index.js' { import { fi } from 'date-fns/esm/locale' export default fi @@ -16367,7 +16411,8 @@ interface dateFns { weekStartsOn?: 0 | 1 | 2 | 3 | 4 | 5 | 6 firstWeekContainsDate?: number locale?: Locale - awareOfUnicodeTokens?: boolean + useAdditionalWeekYearTokens?: boolean + useAdditionalDayOfYearTokens?: boolean } ): string @@ -16577,7 +16622,8 @@ interface dateFns { locale?: Locale weekStartsOn?: 0 | 1 | 2 | 3 | 4 | 5 | 6 firstWeekContainsDate?: 1 | 2 | 3 | 4 | 5 | 6 | 7 - awareOfUnicodeTokens?: boolean + useAdditionalWeekYearTokens?: boolean + useAdditionalDayOfYearTokens?: boolean } ): Date