fecha.js 18 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535
  1. /* Modified from https://github.com/taylorhakes/fecha
  2. * v4.1.0
  3. * hugh zhuang 把 YYYY-MM-DD 改成了 yyyy-MM-dd 与java后台 统一格式
  4. * YYYY修改为yyyy
  5. *
  6. * 备注:未支持多个国际化,该代码参考element-ui的日期帮助类
  7. * 增加日期格式处理
  8. * The MIT License (MIT)
  9. *
  10. * Copyright (c) 2015 Taylor Hakes
  11. *
  12. * Permission is hereby granted, free of charge, to any person obtaining a copy
  13. * of this software and associated documentation files (the "Software"), to deal
  14. * in the Software without restriction, including without limitation the rights
  15. * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
  16. * copies of the Software, and to permit persons to whom the Software is
  17. * furnished to do so, subject to the following conditions:
  18. *
  19. * The above copyright notice and this permission notice shall be included in all
  20. * copies or substantial portions of the Software.
  21. *
  22. * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
  23. * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
  24. * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
  25. * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
  26. * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
  27. * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
  28. * SOFTWARE.
  29. */
  30. var token = /d{1,4}|M{1,4}|yy(?:yy)?|S{1,3}|Do|ZZ|Z|([HhMsDm])\1?|[aA]|"[^"]*"|'[^']*'/g
  31. var twoDigitsOptional = '[1-9]\\d?'
  32. var twoDigits = '\\d\\d'
  33. var threeDigits = '\\d{3}'
  34. var fourDigits = '\\d{4}'
  35. var word = '[^\\s]+'
  36. var literal = /\[([^]*?)\]/gm
  37. function shorten(arr, sLen) {
  38. var newArr = []
  39. for (var i = 0, len = arr.length; i < len; i++) {
  40. newArr.push(arr[i].substr(0, sLen))
  41. }
  42. return newArr
  43. }
  44. var monthUpdate = function(arrName) {
  45. return function(v, i18n) {
  46. var lowerCaseArr = i18n[arrName].map(function(v) { return v.toLowerCase() })
  47. var index = lowerCaseArr.indexOf(v.toLowerCase())
  48. if (index > -1) {
  49. return index
  50. }
  51. return null
  52. }
  53. }
  54. function assign(origObj) {
  55. var args = []
  56. for (var _i = 1; _i < arguments.length; _i++) {
  57. args[_i - 1] = arguments[_i]
  58. }
  59. for (var _a = 0, args_1 = args; _a < args_1.length; _a++) {
  60. var obj = args_1[_a]
  61. for (var key in obj) {
  62. // @ts-ignore ex
  63. origObj[key] = obj[key]
  64. }
  65. }
  66. return origObj
  67. }
  68. var dayNames = [
  69. 'Sunday',
  70. 'Monday',
  71. 'Tuesday',
  72. 'Wednesday',
  73. 'Thursday',
  74. 'Friday',
  75. 'Saturday'
  76. ]
  77. var monthNames = [
  78. 'January',
  79. 'February',
  80. 'March',
  81. 'April',
  82. 'May',
  83. 'June',
  84. 'July',
  85. 'August',
  86. 'September',
  87. 'October',
  88. 'November',
  89. 'December'
  90. ]
  91. var monthNamesShort = shorten(monthNames, 3)
  92. var dayNamesShort = shorten(dayNames, 3)
  93. var defaultI18n = {
  94. dayNamesShort: dayNamesShort,
  95. dayNames: dayNames,
  96. monthNamesShort: monthNamesShort,
  97. monthNames: monthNames,
  98. amPm: ['am', 'pm'],
  99. DoFn: function(dayOfMonth) {
  100. return (dayOfMonth +
  101. ['th', 'st', 'nd', 'rd'][dayOfMonth % 10 > 3
  102. ? 0
  103. : ((dayOfMonth - (dayOfMonth % 10) !== 10 ? 1 : 0) * dayOfMonth) % 10])
  104. }
  105. }
  106. var globalI18n = assign({}, defaultI18n)
  107. var setGlobalDateI18n = function(i18n) {
  108. return (globalI18n = assign(globalI18n, i18n))
  109. }
  110. var regexEscape = function(str) {
  111. return str.replace(/[|\\{()[^$+*?.-]/g, '\\$&')
  112. }
  113. var pad = function(val, len) {
  114. if (len === void 0) { len = 2 }
  115. val = String(val)
  116. while (val.length < len) {
  117. val = '0' + val
  118. }
  119. return val
  120. }
  121. var formatFlags = {
  122. d: function(dateObj) { return String(dateObj.getDate()) }, // zxh D 修改为 d
  123. dd: function(dateObj) { return pad(dateObj.getDate()) }, // zxh DD 修改为 dd
  124. do: function(dateObj, i18n) { // zxh Do 修改为 do
  125. return i18n.DoFn(dateObj.getDate())
  126. },
  127. D: function(dateObj) { return String(dateObj.getDay()) }, // zxh d 修改为D
  128. DD: function(dateObj) { return pad(dateObj.getDay()) }, // zxh dd 修改为 DD
  129. DDD: function(dateObj, i18n) { // zxh ddd 修改为 DDD
  130. return i18n.dayNamesShort[dateObj.getDay()]
  131. },
  132. DDDD: function(dateObj, i18n) { // zxh dddd 修改为 DDDD
  133. return i18n.dayNames[dateObj.getDay()]
  134. },
  135. M: function(dateObj) { return String(dateObj.getMonth() + 1) },
  136. MM: function(dateObj) { return pad(dateObj.getMonth() + 1) },
  137. MMM: function(dateObj, i18n) {
  138. return i18n.monthNamesShort[dateObj.getMonth()]
  139. },
  140. MMMM: function(dateObj, i18n) {
  141. return i18n.monthNames[dateObj.getMonth()]
  142. },
  143. yy: function(dateObj) { // zxh 修改 YY 修改为 yy
  144. return pad(String(dateObj.getFullYear()), 4).substr(2)
  145. },
  146. yyyy: function(dateObj) { return pad(dateObj.getFullYear(), 4) }, // zxh 修改 YYYY 修改为 yyyy
  147. h: function(dateObj) { return String(dateObj.getHours() % 12 || 12) },
  148. hh: function(dateObj) { return pad(dateObj.getHours() % 12 || 12) },
  149. H: function(dateObj) { return String(dateObj.getHours()) },
  150. HH: function(dateObj) { return pad(dateObj.getHours()) },
  151. m: function(dateObj) { return String(dateObj.getMinutes()) },
  152. mm: function(dateObj) { return pad(dateObj.getMinutes()) },
  153. s: function(dateObj) { return String(dateObj.getSeconds()) },
  154. ss: function(dateObj) { return pad(dateObj.getSeconds()) },
  155. S: function(dateObj) {
  156. return String(Math.round(dateObj.getMilliseconds() / 100))
  157. },
  158. SS: function(dateObj) {
  159. return pad(Math.round(dateObj.getMilliseconds() / 10), 2)
  160. },
  161. SSS: function(dateObj) { return pad(dateObj.getMilliseconds(), 3) },
  162. a: function(dateObj, i18n) {
  163. return dateObj.getHours() < 12 ? i18n.amPm[0] : i18n.amPm[1]
  164. },
  165. A: function(dateObj, i18n) {
  166. return dateObj.getHours() < 12
  167. ? i18n.amPm[0].toUpperCase()
  168. : i18n.amPm[1].toUpperCase()
  169. },
  170. ZZ: function(dateObj) {
  171. var offset = dateObj.getTimezoneOffset()
  172. return ((offset > 0 ? '-' : '+') +
  173. pad(Math.floor(Math.abs(offset) / 60) * 100 + (Math.abs(offset) % 60), 4))
  174. },
  175. Z: function(dateObj) {
  176. var offset = dateObj.getTimezoneOffset()
  177. return ((offset > 0 ? '-' : '+') +
  178. pad(Math.floor(Math.abs(offset) / 60), 2) +
  179. ':' +
  180. pad(Math.abs(offset) % 60, 2))
  181. }
  182. }
  183. var monthParse = function(v) { return +v - 1 }
  184. var emptyDigits = [null, twoDigitsOptional]
  185. var emptyWord = [null, word]
  186. var amPm = [
  187. 'isPm',
  188. word,
  189. function(v, i18n) {
  190. var val = v.toLowerCase()
  191. if (val === i18n.amPm[0]) {
  192. return 0
  193. } else if (val === i18n.amPm[1]) {
  194. return 1
  195. }
  196. return null
  197. }
  198. ]
  199. var timezoneOffset = [
  200. 'timezoneOffset',
  201. '[^\\s]*?[\\+\\-]\\d\\d:?\\d\\d|[^\\s]*?Z?',
  202. function(v) {
  203. var parts = (v + '').match(/([+-]|\d\d)/gi)
  204. if (parts) {
  205. var minutes = +parts[1] * 60 + parseInt(parts[2], 10)
  206. return parts[0] === '+' ? minutes : -minutes
  207. }
  208. return 0
  209. }
  210. ]
  211. var parseFlags = {
  212. d: ['day', twoDigitsOptional], // zxh D 修改为 d
  213. dd: ['day', twoDigits], // zxh DD 修改为 dd
  214. do: ['day', twoDigitsOptional + word, function(v) { return parseInt(v, 10) }], // zxh D0 修改为 do
  215. M: ['month', twoDigitsOptional, monthParse],
  216. MM: ['month', twoDigits, monthParse],
  217. YY: [
  218. 'year',
  219. twoDigits,
  220. function(v) {
  221. var now = new Date()
  222. var cent = +('' + now.getFullYear()).substr(0, 2)
  223. return +('' + (+v > 68 ? cent - 1 : cent) + v)
  224. }
  225. ],
  226. h: ['hour', twoDigitsOptional, undefined, 'isPm'],
  227. hh: ['hour', twoDigits, undefined, 'isPm'],
  228. H: ['hour', twoDigitsOptional],
  229. HH: ['hour', twoDigits],
  230. m: ['minute', twoDigitsOptional],
  231. mm: ['minute', twoDigits],
  232. s: ['second', twoDigitsOptional],
  233. ss: ['second', twoDigits],
  234. yyyy: ['year', fourDigits], // zxh YYYY修改为yyyy
  235. S: ['millisecond', '\\d', function(v) { return +v * 100 }],
  236. SS: ['millisecond', twoDigits, function(v) { return +v * 10 }],
  237. SSS: ['millisecond', threeDigits],
  238. D: emptyDigits, // zxh d 修改为 D
  239. DD: emptyDigits, // zxh dd 修改为 DD
  240. DDD: emptyWord,
  241. DDDD: emptyWord,
  242. MMM: ['month', word, monthUpdate('monthNamesShort')],
  243. MMMM: ['month', word, monthUpdate('monthNames')],
  244. a: amPm,
  245. A: amPm,
  246. ZZ: timezoneOffset,
  247. Z: timezoneOffset
  248. }
  249. // Some common format strings
  250. var globalMasks = {
  251. default: 'yyyy-MM-dd HH:mm:ss',
  252. shortDate: 'M/d/yy',
  253. mediumDate: 'MMM D, yyyy',
  254. longDate: 'MMMM d, yyyy',
  255. fullDate: 'DDDD, MMMM d, yyyy',
  256. isoDate: 'yyyy-MM-dd',
  257. isoDateTime: 'yyyy-MM-ddTHH:mm:ssZ',
  258. shortTime: 'HH:mm',
  259. mediumTime: 'HH:mm:ss',
  260. longTime: 'HH:mm:ss.SSS'
  261. }
  262. var setGlobalDateMasks = function(masks) { return assign(globalMasks, masks) }
  263. /** *
  264. * Format a date
  265. * @method format
  266. * @param {Date|number} dateObj
  267. * @param {string} mask Format of the date, i.e. 'mm-dd-yy' or 'shortDate'
  268. * @returns {string} Formatted date string
  269. */
  270. var format = function(dateObj, mask, i18n) {
  271. if (dateObj === null || dateObj === undefined) return ''
  272. if (mask === void 0) { mask = globalMasks['default'] }
  273. if (i18n === void 0) { i18n = {} }
  274. if (typeof dateObj === 'number') {
  275. dateObj = new Date(dateObj)
  276. }
  277. if (Object.prototype.toString.call(dateObj) !== '[object Date]' ||
  278. isNaN(dateObj.getTime())) {
  279. throw new Error('Invalid Date pass to format')
  280. }
  281. mask = globalMasks[mask] || mask
  282. var literals = []
  283. // Make literals inactive by replacing them with @@@
  284. mask = mask.replace(literal, function($0, $1) {
  285. literals.push($1)
  286. return '@@@'
  287. })
  288. var combinedI18nSettings = assign(assign({}, globalI18n), i18n)
  289. // Apply formatting rules
  290. mask = mask.replace(token, function($0) {
  291. return formatFlags[$0](dateObj, combinedI18nSettings)
  292. })
  293. // Inline literal values back into the formatted value
  294. return mask.replace(/@@@/g, function() { return literals.shift() })
  295. }
  296. /**
  297. * Parse a date string into a Javascript Date object /
  298. * @method parse
  299. * @param {string} dateStr Date string
  300. * @param {string} format Date parse format
  301. * @param {i18n} I18nSettingsOptional Full or subset of I18N settings
  302. * @returns {Date|null} Returns Date object. Returns null what date string is invalid or doesn't match format
  303. */
  304. function parse(dateStr, format, i18n) {
  305. if (dateStr === null || dateStr === undefined) return ''
  306. if (i18n === void 0) { i18n = {} }
  307. if (typeof format !== 'string') {
  308. throw new Error('Invalid format in fecha parse')
  309. }
  310. // Check to see if the format is actually a mask
  311. format = globalMasks[format] || format
  312. // Avoid regular expression denial of service, fail early for really long strings
  313. // https://www.owasp.org/index.php/Regular_expression_Denial_of_Service_-_ReDoS
  314. if (dateStr.length > 1000) {
  315. return null
  316. }
  317. // Default to the beginning of the year.
  318. var today = new Date()
  319. var dateInfo = {
  320. year: today.getFullYear(),
  321. month: 0,
  322. day: 1,
  323. hour: 0,
  324. minute: 0,
  325. second: 0,
  326. millisecond: 0,
  327. isPm: null,
  328. timezoneOffset: null
  329. }
  330. var parseInfo = []
  331. var literals = []
  332. // Replace all the literals with @@@. Hopefully a string that won't exist in the format
  333. var newFormat = format.replace(literal, function($0, $1) {
  334. literals.push(regexEscape($1))
  335. return '@@@'
  336. })
  337. var specifiedFields = {}
  338. var requiredFields = {}
  339. // Change every token that we find into the correct regex
  340. newFormat = regexEscape(newFormat).replace(token, function($0) {
  341. var info = parseFlags[$0]
  342. var field = info[0]; var regex = info[1]; var requiredField = info[3]
  343. // Check if the person has specified the same field twice. This will lead to confusing results.
  344. if (specifiedFields[field]) {
  345. throw new Error('Invalid format. ' + field + ' specified twice in format')
  346. }
  347. specifiedFields[field] = true
  348. // Check if there are any required fields. For instance, 12 hour time requires AM/PM specified
  349. if (requiredField) {
  350. requiredFields[requiredField] = true
  351. }
  352. parseInfo.push(info)
  353. return '(' + regex + ')'
  354. })
  355. // Check all the required fields are present
  356. Object.keys(requiredFields).forEach(function(field) {
  357. if (!specifiedFields[field]) {
  358. throw new Error('Invalid format. ' + field + ' is required in specified format')
  359. }
  360. })
  361. // Add back all the literals after
  362. newFormat = newFormat.replace(/@@@/g, function() { return literals.shift() })
  363. // Check if the date string matches the format. If it doesn't return null
  364. var matches = dateStr.match(new RegExp(newFormat, 'i'))
  365. if (!matches) {
  366. return null
  367. }
  368. var combinedI18nSettings = assign(assign({}, globalI18n), i18n)
  369. // For each match, call the parser function for that date part
  370. for (var i = 1; i < matches.length; i++) {
  371. var _a = parseInfo[i - 1]; var field = _a[0]; var parser = _a[2]
  372. var value = parser
  373. ? parser(matches[i], combinedI18nSettings)
  374. : +matches[i]
  375. // If the parser can't make sense of the value, return null
  376. if (value == null) {
  377. return null
  378. }
  379. dateInfo[field] = value
  380. }
  381. if (dateInfo.isPm === 1 && dateInfo.hour != null && +dateInfo.hour !== 12) {
  382. dateInfo.hour = +dateInfo.hour + 12
  383. } else if (dateInfo.isPm === 0 && +dateInfo.hour === 12) {
  384. dateInfo.hour = 0
  385. }
  386. var dateWithoutTZ = new Date(dateInfo.year, dateInfo.month, dateInfo.day, dateInfo.hour, dateInfo.minute, dateInfo.second, dateInfo.millisecond)
  387. var validateFields = [
  388. ['month', 'getMonth'],
  389. ['day', 'getDate'],
  390. ['hour', 'getHours'],
  391. ['minute', 'getMinutes'],
  392. ['second', 'getSeconds']
  393. ]
  394. for (var j = 0, len = validateFields.length; j < len; j++) {
  395. // Check to make sure the date field is within the allowed range. Javascript dates allows values
  396. // outside the allowed range. If the values don't match the value was invalid
  397. if (specifiedFields[validateFields[j][0]] &&
  398. dateInfo[validateFields[j][0]] !== dateWithoutTZ[validateFields[j][1]]()) {
  399. return null
  400. }
  401. }
  402. if (dateInfo.timezoneOffset == null) {
  403. return dateWithoutTZ
  404. }
  405. return new Date(Date.UTC(dateInfo.year, dateInfo.month, dateInfo.day, dateInfo.hour, dateInfo.minute - dateInfo.timezoneOffset, dateInfo.second, dateInfo.millisecond))
  406. }
  407. /**
  408. * 格式化当前时间
  409. */
  410. function formatDate(mask = globalMasks.default, i18nSettings) {
  411. return format(new Date(), mask, i18nSettings)
  412. }
  413. /**
  414. * 格式当前时间
  415. */
  416. function parseDate(mask = globalMasks.default, i18nSettings) {
  417. return parse(formatDate(mask, i18nSettings), mask, i18nSettings)
  418. }
  419. /**
  420. * 相对时间字符串
  421. * @param {String|Number} time 时间格式字符串,或者时间
  422. * @returns {String} 相对时间字符串
  423. */
  424. function formatRelativeTime(time, mask = {}, i18nSettings) {
  425. if (!i18nSettings) {
  426. i18nSettings = function() {}
  427. }
  428. if (!time || time === null) return ''
  429. let date
  430. if (Object.prototype.toString.call(time) === '[object Date]') {
  431. date = time
  432. } else {
  433. date = !isNaN(time) ? new Date(time) : parse(time, mask['orig'] || globalMasks.default)
  434. }
  435. const timeStamp = date.getTime()
  436. // 获取当前时间时间戳
  437. const currentTime = (new Date()).getTime()
  438. // 判断传入时间戳是否早于当前时间戳
  439. const IS_EARLY = timeStamp <= currentTime
  440. // 获取两个时间戳差值
  441. let diff = currentTime - timeStamp
  442. // 如果IS_EARLY为false则差值取反
  443. if (!IS_EARLY) diff = -diff
  444. let resStr = ''
  445. const dirStr = IS_EARLY ? (i18nSettings('ibps.time.before') || '前') : (i18nSettings('ibps.time.after') || '后')
  446. if (diff < 1000) {
  447. resStr = i18nSettings('ibps.time.just') || '刚刚'
  448. } else if (diff < 60000) {
  449. // 少于等于59秒
  450. resStr = parseInt(diff / 1000) + (i18nSettings('ibps.time.seconds') || '秒') + dirStr
  451. } else if (diff >= 60000 && diff < 3600000) {
  452. // 多于59秒,少于等于59分钟59秒
  453. resStr = Math.floor(diff / 60000) + (i18nSettings('ibps.time.minutes') || '分钟') + dirStr
  454. } else if (diff >= 3600000 && diff < 86400000) {
  455. // 多于59分钟59秒,少于等于23小时59分钟59秒
  456. resStr = Math.floor(diff / 3600000) + (i18nSettings('ibps.time.hours') || '小时') + dirStr
  457. } else if (diff >= 86400000 && diff < 2623860000) {
  458. // 多于23小时59分钟59秒,少于等于29天59分钟59秒
  459. resStr = Math.floor(diff / 86400000) + (i18nSettings('ibps.time.days') || '天') + dirStr
  460. } else if (diff >= 2623860000 && diff <= 31567860000 && IS_EARLY) {
  461. // 多于29天59分钟59秒,少于364天23小时59分钟59秒,且传入的时间戳早于当前
  462. resStr = format(timeStamp, mask['day'] || 'MM-dd HH:mm')
  463. } else {
  464. resStr = format(timeStamp, mask['year'] || globalMasks.default)
  465. }
  466. return resStr
  467. }
  468. const dateDealFmt = {
  469. $dp: {
  470. has: {}
  471. },
  472. dealFmt: function(dateStr, dateFmt) {
  473. if (dateStr === '' || dateStr === null || dateStr === undefined) { return null }
  474. if (dateStr.length !== dateFmt.length) { // 格式化日期不相同
  475. const date = new Date(dateStr.replace(/-/g, '/'))
  476. if (!isNaN(date.getTime())) {
  477. return date
  478. } else { // IE
  479. const mydate = dateStr.slice(0, dateStr.indexOf('.'))// 去掉毫秒数
  480. return new Date(mydate.replace(/-/g, '/'))
  481. }
  482. }
  483. this.$dp.dateFmt = dateFmt
  484. this._setHas(/w/)
  485. this._setHas(/WW|W/)
  486. this._setHas(/DD|D/)
  487. this._setHas(/yyyy|yyy|yy|y/)
  488. this._setHas(/MMMM|MMM|MM|M/)
  489. this._setHas(/dd|d/)
  490. this._setHas(/HH|H/)
  491. this._setHas(/mm|m/)
  492. this._setHas(/ss|s/)
  493. const date = new Date()
  494. for (const p in this.$dp.has) {
  495. const has = this.$dp.has[p]
  496. if (has != null) {
  497. const val = parseInt(dateStr.substring(has.index, has.index + has[0].length), 10)
  498. if (p === 'y') { date.setYear(val) }
  499. if (p === 'M') { date.setMonth(val - 1, 1) }
  500. if (p === 'd') { date.setDate(val) }
  501. if (p === 'H') { date.setHours(val) }
  502. if (p === 'm') { date.setMinutes(val) }
  503. if (p === 's') { date.setSeconds(val) }
  504. }
  505. }
  506. return date
  507. },
  508. _setHas: function(re) {
  509. this.$dp.has[(re + '').slice(1, 2)] = re.exec(this.$dp.dateFmt)
  510. }
  511. }
  512. var fecha = {
  513. format: format,
  514. parse: parse,
  515. defaultI18n: defaultI18n,
  516. setGlobalDateI18n: setGlobalDateI18n,
  517. setGlobalDateMasks: setGlobalDateMasks,
  518. formatDate: formatDate,
  519. parseDate: parseDate,
  520. formatRelativeTime: formatRelativeTime
  521. }
  522. export default fecha
  523. export { assign, format, parse, defaultI18n, setGlobalDateI18n, setGlobalDateMasks, formatDate, parseDate, formatRelativeTime, dateDealFmt }