From 15b5ba90b9090cb4421936bdcbe224dd0f8f3d6b Mon Sep 17 00:00:00 2001 From: vladislav-karamfilov Date: Tue, 30 Jul 2024 09:56:41 +0300 Subject: [PATCH] fix: ensure dates are parsed timezone agnostically Closes #1223 --- package-lock.json | 14 ++++++++------ packages/form-js-viewer/package.json | 1 + .../render/components/form-fields/Datetime.js | 3 ++- .../src/render/components/util/dateTimeUtil.js | 18 ++++++++---------- 4 files changed, 19 insertions(+), 17 deletions(-) diff --git a/package-lock.json b/package-lock.json index 14b3f745a..40dff4c94 100644 --- a/package-lock.json +++ b/package-lock.json @@ -14126,9 +14126,9 @@ } }, "node_modules/luxon": { - "version": "3.4.4", - "resolved": "https://registry.npmjs.org/luxon/-/luxon-3.4.4.tgz", - "integrity": "sha512-zobTr7akeGHnv7eBOXcRgMeCP6+uyYsczwmeRCauvpvaAltgNyTbLH/+VaEAPUeWBT+1GuNmz4wC/6jtQzbbVA==", + "version": "3.5.0", + "resolved": "https://registry.npmjs.org/luxon/-/luxon-3.5.0.tgz", + "integrity": "sha512-rh+Zjr6DNfUYR3bPwJEnuwDdqMbxZW7LOQfUN4B54+Cl+0o5zaU9RJ6bcidfDtC1cWCZXQ+nvX8bf6bAji37QQ==", "engines": { "node": ">=12" } @@ -21317,6 +21317,7 @@ "flatpickr": "^4.6.13", "ids": "^1.0.5", "lodash": "^4.17.21", + "luxon": "^3.5.0", "marked": "^13.0.0", "min-dash": "^4.2.1", "preact": "^10.5.14" @@ -22826,6 +22827,7 @@ "flatpickr": "^4.6.13", "ids": "^1.0.5", "lodash": "^4.17.21", + "luxon": "*", "marked": "^13.0.0", "min-dash": "^4.2.1", "preact": "^10.5.14" @@ -31226,9 +31228,9 @@ } }, "luxon": { - "version": "3.4.4", - "resolved": "https://registry.npmjs.org/luxon/-/luxon-3.4.4.tgz", - "integrity": "sha512-zobTr7akeGHnv7eBOXcRgMeCP6+uyYsczwmeRCauvpvaAltgNyTbLH/+VaEAPUeWBT+1GuNmz4wC/6jtQzbbVA==" + "version": "3.5.0", + "resolved": "https://registry.npmjs.org/luxon/-/luxon-3.5.0.tgz", + "integrity": "sha512-rh+Zjr6DNfUYR3bPwJEnuwDdqMbxZW7LOQfUN4B54+Cl+0o5zaU9RJ6bcidfDtC1cWCZXQ+nvX8bf6bAji37QQ==" }, "lz-string": { "version": "1.4.4", diff --git a/packages/form-js-viewer/package.json b/packages/form-js-viewer/package.json index 2a67fe03b..0f8c2b533 100644 --- a/packages/form-js-viewer/package.json +++ b/packages/form-js-viewer/package.json @@ -55,6 +55,7 @@ "flatpickr": "^4.6.13", "ids": "^1.0.5", "lodash": "^4.17.21", + "luxon": "^3.5.0", "marked": "^13.0.0", "min-dash": "^4.2.1", "preact": "^10.5.14" diff --git a/packages/form-js-viewer/src/render/components/form-fields/Datetime.js b/packages/form-js-viewer/src/render/components/form-fields/Datetime.js index d7edefd9c..d1b819d94 100644 --- a/packages/form-js-viewer/src/render/components/form-fields/Datetime.js +++ b/packages/form-js-viewer/src/render/components/form-fields/Datetime.js @@ -1,4 +1,5 @@ import { useCallback, useContext, useMemo, useState, useEffect, useRef } from 'preact/hooks'; +import { DateTime as LuxonDateTime } from 'luxon'; import classNames from 'classnames'; @@ -86,7 +87,7 @@ export function Datetime(props) { switch (subtype) { case DATETIME_SUBTYPES.DATE: { - date = new Date(Date.parse(value)); + date = typeof value === 'string' ? LuxonDateTime.fromISO(value).toJSDate() : new Date(NaN); break; } case DATETIME_SUBTYPES.TIME: { diff --git a/packages/form-js-viewer/src/render/components/util/dateTimeUtil.js b/packages/form-js-viewer/src/render/components/util/dateTimeUtil.js index a2c27de21..c565c30fa 100644 --- a/packages/form-js-viewer/src/render/components/util/dateTimeUtil.js +++ b/packages/form-js-viewer/src/render/components/util/dateTimeUtil.js @@ -1,5 +1,6 @@ import { isNumber } from 'min-dash'; import { MINUTES_IN_DAY, TIME_SERIALISING_FORMATS } from '../../../util/constants/DatetimeConstants'; +import { DateTime as LuxonDateTime } from 'luxon'; export const ENTER_KEYDOWN_EVENT = new KeyboardEvent('keydown', { code: 'Enter', @@ -145,18 +146,15 @@ export function parseIsoTime(isoTimeString) { } } +/** + * Returns the date object as a simple 'YYYY-MM-DD' formatted date in the local timezone. + * + * @param {*} date The date object to serialize. + * @returns {string} The serialized date. + */ export function serializeDate(date) { - var d = new Date(date), - month = '' + (d.getMonth() + 1), - day = '' + d.getDate(), - year = d.getFullYear(); - - if (month.length < 2) month = '0' + month; - if (day.length < 2) day = '0' + day; - - return [year, month, day].join('-'); + return LuxonDateTime.fromJSDate(date).toISODate(); } - // this method is used to make the `new Date(value)` parsing behavior stricter export function isDateTimeInputInformationSufficient(value) { if (!value || typeof value !== 'string') return false;