@neo4j-ndl/react 4.15.2 → 4.15.3
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/lib/cjs/_generated/style-rules/color-utils.js +50 -0
- package/lib/cjs/_generated/style-rules/color-utils.js.map +1 -0
- package/lib/cjs/_generated/style-rules/date-utils.js +145 -0
- package/lib/cjs/_generated/style-rules/date-utils.js.map +1 -0
- package/lib/cjs/_generated/style-rules/index.js +38 -0
- package/lib/cjs/_generated/style-rules/index.js.map +1 -0
- package/lib/cjs/_generated/style-rules/literal-schemas.js +64 -0
- package/lib/cjs/_generated/style-rules/literal-schemas.js.map +1 -0
- package/lib/cjs/data-grid/stories/datagrid-rule-based-styling-datetime.story.js +286 -0
- package/lib/cjs/data-grid/stories/datagrid-rule-based-styling-datetime.story.js.map +1 -0
- package/lib/cjs/data-grid/stories/index.js +5 -1
- package/lib/cjs/data-grid/stories/index.js.map +1 -1
- package/lib/cjs/data-grid/style-rules/evaluate.js +13 -17
- package/lib/cjs/data-grid/style-rules/evaluate.js.map +1 -1
- package/lib/cjs/data-grid/style-rules/index.js +3 -1
- package/lib/cjs/data-grid/style-rules/index.js.map +1 -1
- package/lib/cjs/data-grid/style-rules/types.js +26 -2
- package/lib/cjs/data-grid/style-rules/types.js.map +1 -1
- package/lib/cjs/time-picker/TimePicker.js +36 -20
- package/lib/cjs/time-picker/TimePicker.js.map +1 -1
- package/lib/cjs/time-picker/generate-time-options.js +6 -3
- package/lib/cjs/time-picker/generate-time-options.js.map +1 -1
- package/lib/cjs/time-picker/needle-time.js +23 -9
- package/lib/cjs/time-picker/needle-time.js.map +1 -1
- package/lib/cjs/time-picker/stories/index.js +5 -1
- package/lib/cjs/time-picker/stories/index.js.map +1 -1
- package/lib/cjs/time-picker/stories/time-picker-with-seconds.story.js +32 -0
- package/lib/cjs/time-picker/stories/time-picker-with-seconds.story.js.map +1 -0
- package/lib/esm/_generated/style-rules/color-utils.js +46 -0
- package/lib/esm/_generated/style-rules/color-utils.js.map +1 -0
- package/lib/esm/_generated/style-rules/date-utils.js +141 -0
- package/lib/esm/_generated/style-rules/date-utils.js.map +1 -0
- package/lib/esm/_generated/style-rules/index.js +29 -0
- package/lib/esm/_generated/style-rules/index.js.map +1 -0
- package/lib/esm/_generated/style-rules/literal-schemas.js +61 -0
- package/lib/esm/_generated/style-rules/literal-schemas.js.map +1 -0
- package/lib/esm/data-grid/stories/datagrid-rule-based-styling-datetime.story.js +284 -0
- package/lib/esm/data-grid/stories/datagrid-rule-based-styling-datetime.story.js.map +1 -0
- package/lib/esm/data-grid/stories/index.js +3 -0
- package/lib/esm/data-grid/stories/index.js.map +1 -1
- package/lib/esm/data-grid/style-rules/evaluate.js +7 -11
- package/lib/esm/data-grid/style-rules/evaluate.js.map +1 -1
- package/lib/esm/data-grid/style-rules/index.js +1 -1
- package/lib/esm/data-grid/style-rules/index.js.map +1 -1
- package/lib/esm/data-grid/style-rules/types.js +25 -1
- package/lib/esm/data-grid/style-rules/types.js.map +1 -1
- package/lib/esm/time-picker/TimePicker.js +36 -20
- package/lib/esm/time-picker/TimePicker.js.map +1 -1
- package/lib/esm/time-picker/generate-time-options.js +6 -3
- package/lib/esm/time-picker/generate-time-options.js.map +1 -1
- package/lib/esm/time-picker/needle-time.js +23 -9
- package/lib/esm/time-picker/needle-time.js.map +1 -1
- package/lib/esm/time-picker/stories/index.js +3 -0
- package/lib/esm/time-picker/stories/index.js.map +1 -1
- package/lib/esm/time-picker/stories/time-picker-with-seconds.story.js +30 -0
- package/lib/esm/time-picker/stories/time-picker-with-seconds.story.js.map +1 -0
- package/lib/types/_generated/style-rules/color-utils.d.ts +33 -0
- package/lib/types/_generated/style-rules/color-utils.d.ts.map +1 -0
- package/lib/types/_generated/style-rules/date-utils.d.ts +54 -0
- package/lib/types/_generated/style-rules/date-utils.d.ts.map +1 -0
- package/lib/types/_generated/style-rules/index.d.ts +25 -0
- package/lib/types/_generated/style-rules/index.d.ts.map +1 -0
- package/lib/types/_generated/style-rules/literal-schemas.d.ts +53 -0
- package/lib/types/_generated/style-rules/literal-schemas.d.ts.map +1 -0
- package/lib/types/data-grid/stories/datagrid-rule-based-styling-datetime.story.d.ts +24 -0
- package/lib/types/data-grid/stories/datagrid-rule-based-styling-datetime.story.d.ts.map +1 -0
- package/lib/types/data-grid/stories/index.d.ts +2 -0
- package/lib/types/data-grid/stories/index.d.ts.map +1 -1
- package/lib/types/data-grid/style-rules/evaluate.d.ts.map +1 -1
- package/lib/types/data-grid/style-rules/index.d.ts +2 -2
- package/lib/types/data-grid/style-rules/index.d.ts.map +1 -1
- package/lib/types/data-grid/style-rules/types.d.ts +33 -2
- package/lib/types/data-grid/style-rules/types.d.ts.map +1 -1
- package/lib/types/time-picker/TimePicker.d.ts +1 -1
- package/lib/types/time-picker/TimePicker.d.ts.map +1 -1
- package/lib/types/time-picker/generate-time-options.d.ts +1 -1
- package/lib/types/time-picker/generate-time-options.d.ts.map +1 -1
- package/lib/types/time-picker/needle-time.d.ts +4 -2
- package/lib/types/time-picker/needle-time.d.ts.map +1 -1
- package/lib/types/time-picker/stories/index.d.ts +2 -0
- package/lib/types/time-picker/stories/index.d.ts.map +1 -1
- package/lib/types/time-picker/stories/time-picker-with-seconds.story.d.ts +24 -0
- package/lib/types/time-picker/stories/time-picker-with-seconds.story.d.ts.map +1 -0
- package/package.json +6 -4
|
@@ -0,0 +1,141 @@
|
|
|
1
|
+
/*
|
|
2
|
+
* AUTO-GENERATED FILE — DO NOT EDIT.
|
|
3
|
+
* Source of truth: packages/style-rules/src/
|
|
4
|
+
* Regenerate with `pnpm generate:shared` (runs automatically at build/dev/install).
|
|
5
|
+
*/
|
|
6
|
+
/**
|
|
7
|
+
*
|
|
8
|
+
* Copyright (c) "Neo4j"
|
|
9
|
+
* Neo4j Sweden AB [http://neo4j.com]
|
|
10
|
+
*
|
|
11
|
+
* This file is part of Neo4j.
|
|
12
|
+
*
|
|
13
|
+
* Neo4j is free software: you can redistribute it and/or modify
|
|
14
|
+
* it under the terms of the GNU General Public License as published by
|
|
15
|
+
* the Free Software Foundation, either version 3 of the License, or
|
|
16
|
+
* (at your option) any later version.
|
|
17
|
+
*
|
|
18
|
+
* This program is distributed in the hope that it will be useful,
|
|
19
|
+
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
20
|
+
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
21
|
+
* GNU General Public License for more details.
|
|
22
|
+
*
|
|
23
|
+
* You should have received a copy of the GNU General Public License
|
|
24
|
+
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
|
25
|
+
*/
|
|
26
|
+
import { Temporal } from 'temporal-polyfill';
|
|
27
|
+
const MS_PER_DAY = 86400000;
|
|
28
|
+
function plainTimeToMs(pt) {
|
|
29
|
+
return (pt.hour * 3600000 +
|
|
30
|
+
pt.minute * 60000 +
|
|
31
|
+
pt.second * 1000 +
|
|
32
|
+
pt.millisecond);
|
|
33
|
+
}
|
|
34
|
+
function parseOffsetMs(offsetStr) {
|
|
35
|
+
const match = offsetStr.match(/^([+-])(\d{2}):(\d{2})$/);
|
|
36
|
+
if (!match) {
|
|
37
|
+
return null;
|
|
38
|
+
}
|
|
39
|
+
const sign = match[1] === '+' ? 1 : -1;
|
|
40
|
+
return (sign *
|
|
41
|
+
(parseInt(match[2], 10) * 3600000 + parseInt(match[3], 10) * 60000));
|
|
42
|
+
}
|
|
43
|
+
/**
|
|
44
|
+
* Parses an ISO 8601 time string to UTC milliseconds since midnight
|
|
45
|
+
* (0–86,399,999). Returns `null` if the string cannot be parsed.
|
|
46
|
+
*
|
|
47
|
+
* Three formats are accepted:
|
|
48
|
+
* 1. Local time (no offset): `"14:30:00"`, `"14:30:00.500"` — treated as UTC
|
|
49
|
+
* 2. UTC time with Z suffix: `"14:30:00Z"` — treated identically to the local form
|
|
50
|
+
* 3. Offset time: `"14:30:00+02:00"` — the offset is applied so the result
|
|
51
|
+
* is the equivalent UTC time of day. `"12:00:00+01:00"` resolves to
|
|
52
|
+
* 39,600,000 (11:00 UTC), which is less than `"12:00:00+00:00"` (43,200,000).
|
|
53
|
+
*
|
|
54
|
+
* Values wrap around midnight: `"00:00:00+01:00"` → 82,800,000 (23:00 UTC).
|
|
55
|
+
*/
|
|
56
|
+
export function parseTimeString(s) {
|
|
57
|
+
// Reject datetime strings and anything with an IANA timezone bracket.
|
|
58
|
+
// Temporal.PlainTime.from silently extracts the time portion from strings
|
|
59
|
+
// containing a 'T' separator. IANA brackets are meaningless for time-only
|
|
60
|
+
// values (there is no date to anchor DST to), so they are also rejected.
|
|
61
|
+
if (s.includes('T') || s.includes('[')) {
|
|
62
|
+
return null;
|
|
63
|
+
}
|
|
64
|
+
// Offset time: detect "+HH:MM" or "-HH:MM" suffix first. Temporal.PlainTime.from
|
|
65
|
+
// silently strips offsets and returns the clock-face time, so we must handle
|
|
66
|
+
// offset strings explicitly before falling through to the plain parse.
|
|
67
|
+
const offsetMatch = s.match(/([+-]\d{2}:\d{2})(\[.*\])?$/);
|
|
68
|
+
if (offsetMatch) {
|
|
69
|
+
const offsetStr = offsetMatch[1];
|
|
70
|
+
const timeStr = s.slice(0, s.indexOf(offsetStr));
|
|
71
|
+
const offsetMs = parseOffsetMs(offsetStr);
|
|
72
|
+
if (offsetMs !== null) {
|
|
73
|
+
try {
|
|
74
|
+
const localMs = plainTimeToMs(Temporal.PlainTime.from(timeStr));
|
|
75
|
+
// Subtract the UTC offset to normalise to UTC time-of-day; wrap around midnight
|
|
76
|
+
return (((localMs - offsetMs) % MS_PER_DAY) + MS_PER_DAY) % MS_PER_DAY;
|
|
77
|
+
}
|
|
78
|
+
catch (_a) {
|
|
79
|
+
/* empty */
|
|
80
|
+
}
|
|
81
|
+
}
|
|
82
|
+
return null;
|
|
83
|
+
}
|
|
84
|
+
// UTC time with Z suffix (e.g. "14:30:00Z") — strip Z and treat as local (UTC) time.
|
|
85
|
+
// Only apply when there is no 'T' in the string; a datetime string like
|
|
86
|
+
// "2024-06-15T14:30:00Z" must not be accepted here.
|
|
87
|
+
const normalized = s.endsWith('Z') && !s.includes('T') ? s.slice(0, -1) : s;
|
|
88
|
+
// Local time (no offset) — treated as UTC
|
|
89
|
+
try {
|
|
90
|
+
return plainTimeToMs(Temporal.PlainTime.from(normalized));
|
|
91
|
+
}
|
|
92
|
+
catch (_b) {
|
|
93
|
+
/* empty */
|
|
94
|
+
}
|
|
95
|
+
return null;
|
|
96
|
+
}
|
|
97
|
+
/**
|
|
98
|
+
* Parses an ISO 8601 or RFC 9557 date/datetime string to a Unix millisecond
|
|
99
|
+
* timestamp. Returns `null` if the string cannot be parsed.
|
|
100
|
+
*
|
|
101
|
+
* Three formats are tried in order:
|
|
102
|
+
* 1. RFC 9557 ZonedDateTime with IANA bracket notation
|
|
103
|
+
* e.g. `"2024-06-15T14:00:00[Europe/Stockholm]"` (offset inferred from the
|
|
104
|
+
* named timezone, including DST) or `"2024-06-15T14:00:00+02:00[Europe/Stockholm]"`
|
|
105
|
+
* (offset explicit; bracket must agree with the IANA zone)
|
|
106
|
+
* 2. UTC or fixed-offset Instant
|
|
107
|
+
* e.g. `"2024-01-01T00:00:00Z"`, `"2024-01-01T00:00:00+02:00"`
|
|
108
|
+
* 3. Plain date or datetime (no offset, `Z`, or IANA bracket), interpreted as UTC
|
|
109
|
+
* e.g. `"2024-01-01"`, `"2024-01-01T14:30:00"`, `"2024-01-01T14:30:00.500"`
|
|
110
|
+
*
|
|
111
|
+
* Strings with a time component that lack `Z`, an offset, or an IANA bracket are
|
|
112
|
+
* parsed as UTC wall-clock time (same semantics as Neo4j `LocalDateTime`).
|
|
113
|
+
*/
|
|
114
|
+
export function parseDateString(s) {
|
|
115
|
+
// RFC 9557 / ZonedDateTime with IANA bracket notation
|
|
116
|
+
try {
|
|
117
|
+
return Temporal.ZonedDateTime.from(s).epochMilliseconds;
|
|
118
|
+
}
|
|
119
|
+
catch (_a) {
|
|
120
|
+
/* empty */
|
|
121
|
+
}
|
|
122
|
+
// UTC or fixed-offset datetime (no IANA name)
|
|
123
|
+
try {
|
|
124
|
+
return Temporal.Instant.from(s).epochMilliseconds;
|
|
125
|
+
}
|
|
126
|
+
catch (_b) {
|
|
127
|
+
/* empty */
|
|
128
|
+
}
|
|
129
|
+
// Plain datetime — interpret as UTC.
|
|
130
|
+
// Also covers date-only strings like "2024-01-01" (PlainDateTime.from parses
|
|
131
|
+
// them as midnight), so a separate PlainDate path is not needed.
|
|
132
|
+
try {
|
|
133
|
+
return Temporal.PlainDateTime.from(s).toZonedDateTime('UTC')
|
|
134
|
+
.epochMilliseconds;
|
|
135
|
+
}
|
|
136
|
+
catch (_c) {
|
|
137
|
+
/* empty */
|
|
138
|
+
}
|
|
139
|
+
return null;
|
|
140
|
+
}
|
|
141
|
+
//# sourceMappingURL=date-utils.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"date-utils.js","sourceRoot":"","sources":["../../../../src/_generated/style-rules/date-utils.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAEH;;;;;;;;;;;;;;;;;;;GAmBG;AAEH,OAAO,EAAE,QAAQ,EAAE,MAAM,mBAAmB,CAAC;AAE7C,MAAM,UAAU,GAAG,QAAU,CAAC;AAE9B,SAAS,aAAa,CAAC,EAAsB;IAC3C,OAAO,CACL,EAAE,CAAC,IAAI,GAAG,OAAS;QACnB,EAAE,CAAC,MAAM,GAAG,KAAM;QAClB,EAAE,CAAC,MAAM,GAAG,IAAK;QACjB,EAAE,CAAC,WAAW,CACf,CAAC;AACJ,CAAC;AAED,SAAS,aAAa,CAAC,SAAiB;IACtC,MAAM,KAAK,GAAG,SAAS,CAAC,KAAK,CAAC,yBAAyB,CAAC,CAAC;IACzD,IAAI,CAAC,KAAK,EAAE,CAAC;QACX,OAAO,IAAI,CAAC;IACd,CAAC;IACD,MAAM,IAAI,GAAG,KAAK,CAAC,CAAC,CAAC,KAAK,GAAG,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IACvC,OAAO,CACL,IAAI;QACJ,CAAC,QAAQ,CAAC,KAAK,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,GAAG,OAAS,GAAG,QAAQ,CAAC,KAAK,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,GAAG,KAAM,CAAC,CACvE,CAAC;AACJ,CAAC;AAED;;;;;;;;;;;;GAYG;AACH,MAAM,UAAU,eAAe,CAAC,CAAS;IACvC,sEAAsE;IACtE,0EAA0E;IAC1E,0EAA0E;IAC1E,yEAAyE;IACzE,IAAI,CAAC,CAAC,QAAQ,CAAC,GAAG,CAAC,IAAI,CAAC,CAAC,QAAQ,CAAC,GAAG,CAAC,EAAE,CAAC;QACvC,OAAO,IAAI,CAAC;IACd,CAAC;IACD,iFAAiF;IACjF,6EAA6E;IAC7E,uEAAuE;IACvE,MAAM,WAAW,GAAG,CAAC,CAAC,KAAK,CAAC,6BAA6B,CAAC,CAAC;IAC3D,IAAI,WAAW,EAAE,CAAC;QAChB,MAAM,SAAS,GAAG,WAAW,CAAC,CAAC,CAAC,CAAC;QACjC,MAAM,OAAO,GAAG,CAAC,CAAC,KAAK,CAAC,CAAC,EAAE,CAAC,CAAC,OAAO,CAAC,SAAS,CAAC,CAAC,CAAC;QACjD,MAAM,QAAQ,GAAG,aAAa,CAAC,SAAS,CAAC,CAAC;QAC1C,IAAI,QAAQ,KAAK,IAAI,EAAE,CAAC;YACtB,IAAI,CAAC;gBACH,MAAM,OAAO,GAAG,aAAa,CAAC,QAAQ,CAAC,SAAS,CAAC,IAAI,CAAC,OAAO,CAAC,CAAC,CAAC;gBAChE,gFAAgF;gBAChF,OAAO,CAAC,CAAC,CAAC,OAAO,GAAG,QAAQ,CAAC,GAAG,UAAU,CAAC,GAAG,UAAU,CAAC,GAAG,UAAU,CAAC;YACzE,CAAC;YAAC,WAAM,CAAC;gBACP,WAAW;YACb,CAAC;QACH,CAAC;QACD,OAAO,IAAI,CAAC;IACd,CAAC;IAED,qFAAqF;IACrF,wEAAwE;IACxE,oDAAoD;IACpD,MAAM,UAAU,GAAG,CAAC,CAAC,QAAQ,CAAC,GAAG,CAAC,IAAI,CAAC,CAAC,CAAC,QAAQ,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IAE5E,0CAA0C;IAC1C,IAAI,CAAC;QACH,OAAO,aAAa,CAAC,QAAQ,CAAC,SAAS,CAAC,IAAI,CAAC,UAAU,CAAC,CAAC,CAAC;IAC5D,CAAC;IAAC,WAAM,CAAC;QACP,WAAW;IACb,CAAC;IAED,OAAO,IAAI,CAAC;AACd,CAAC;AAED;;;;;;;;;;;;;;;;GAgBG;AACH,MAAM,UAAU,eAAe,CAAC,CAAS;IACvC,sDAAsD;IACtD,IAAI,CAAC;QACH,OAAO,QAAQ,CAAC,aAAa,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC,iBAAiB,CAAC;IAC1D,CAAC;IAAC,WAAM,CAAC;QACP,WAAW;IACb,CAAC;IAED,8CAA8C;IAC9C,IAAI,CAAC;QACH,OAAO,QAAQ,CAAC,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC,iBAAiB,CAAC;IACpD,CAAC;IAAC,WAAM,CAAC;QACP,WAAW;IACb,CAAC;IAED,qCAAqC;IACrC,6EAA6E;IAC7E,iEAAiE;IACjE,IAAI,CAAC;QACH,OAAO,QAAQ,CAAC,aAAa,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC,eAAe,CAAC,KAAK,CAAC;aACzD,iBAAiB,CAAC;IACvB,CAAC;IAAC,WAAM,CAAC;QACP,WAAW;IACb,CAAC;IAED,OAAO,IAAI,CAAC;AACd,CAAC","sourcesContent":["/*\n * AUTO-GENERATED FILE — DO NOT EDIT.\n * Source of truth: packages/style-rules/src/\n * Regenerate with `pnpm generate:shared` (runs automatically at build/dev/install).\n */\n\n/**\n *\n * Copyright (c) \"Neo4j\"\n * Neo4j Sweden AB [http://neo4j.com]\n *\n * This file is part of Neo4j.\n *\n * Neo4j is free software: you can redistribute it and/or modify\n * it under the terms of the GNU General Public License as published by\n * the Free Software Foundation, either version 3 of the License, or\n * (at your option) any later version.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program. If not, see <http://www.gnu.org/licenses/>.\n */\n\nimport { Temporal } from 'temporal-polyfill';\n\nconst MS_PER_DAY = 86_400_000;\n\nfunction plainTimeToMs(pt: Temporal.PlainTime): number {\n return (\n pt.hour * 3_600_000 +\n pt.minute * 60_000 +\n pt.second * 1_000 +\n pt.millisecond\n );\n}\n\nfunction parseOffsetMs(offsetStr: string): number | null {\n const match = offsetStr.match(/^([+-])(\\d{2}):(\\d{2})$/);\n if (!match) {\n return null;\n }\n const sign = match[1] === '+' ? 1 : -1;\n return (\n sign *\n (parseInt(match[2], 10) * 3_600_000 + parseInt(match[3], 10) * 60_000)\n );\n}\n\n/**\n * Parses an ISO 8601 time string to UTC milliseconds since midnight\n * (0–86,399,999). Returns `null` if the string cannot be parsed.\n *\n * Three formats are accepted:\n * 1. Local time (no offset): `\"14:30:00\"`, `\"14:30:00.500\"` — treated as UTC\n * 2. UTC time with Z suffix: `\"14:30:00Z\"` — treated identically to the local form\n * 3. Offset time: `\"14:30:00+02:00\"` — the offset is applied so the result\n * is the equivalent UTC time of day. `\"12:00:00+01:00\"` resolves to\n * 39,600,000 (11:00 UTC), which is less than `\"12:00:00+00:00\"` (43,200,000).\n *\n * Values wrap around midnight: `\"00:00:00+01:00\"` → 82,800,000 (23:00 UTC).\n */\nexport function parseTimeString(s: string): number | null {\n // Reject datetime strings and anything with an IANA timezone bracket.\n // Temporal.PlainTime.from silently extracts the time portion from strings\n // containing a 'T' separator. IANA brackets are meaningless for time-only\n // values (there is no date to anchor DST to), so they are also rejected.\n if (s.includes('T') || s.includes('[')) {\n return null;\n }\n // Offset time: detect \"+HH:MM\" or \"-HH:MM\" suffix first. Temporal.PlainTime.from\n // silently strips offsets and returns the clock-face time, so we must handle\n // offset strings explicitly before falling through to the plain parse.\n const offsetMatch = s.match(/([+-]\\d{2}:\\d{2})(\\[.*\\])?$/);\n if (offsetMatch) {\n const offsetStr = offsetMatch[1];\n const timeStr = s.slice(0, s.indexOf(offsetStr));\n const offsetMs = parseOffsetMs(offsetStr);\n if (offsetMs !== null) {\n try {\n const localMs = plainTimeToMs(Temporal.PlainTime.from(timeStr));\n // Subtract the UTC offset to normalise to UTC time-of-day; wrap around midnight\n return (((localMs - offsetMs) % MS_PER_DAY) + MS_PER_DAY) % MS_PER_DAY;\n } catch {\n /* empty */\n }\n }\n return null;\n }\n\n // UTC time with Z suffix (e.g. \"14:30:00Z\") — strip Z and treat as local (UTC) time.\n // Only apply when there is no 'T' in the string; a datetime string like\n // \"2024-06-15T14:30:00Z\" must not be accepted here.\n const normalized = s.endsWith('Z') && !s.includes('T') ? s.slice(0, -1) : s;\n\n // Local time (no offset) — treated as UTC\n try {\n return plainTimeToMs(Temporal.PlainTime.from(normalized));\n } catch {\n /* empty */\n }\n\n return null;\n}\n\n/**\n * Parses an ISO 8601 or RFC 9557 date/datetime string to a Unix millisecond\n * timestamp. Returns `null` if the string cannot be parsed.\n *\n * Three formats are tried in order:\n * 1. RFC 9557 ZonedDateTime with IANA bracket notation\n * e.g. `\"2024-06-15T14:00:00[Europe/Stockholm]\"` (offset inferred from the\n * named timezone, including DST) or `\"2024-06-15T14:00:00+02:00[Europe/Stockholm]\"`\n * (offset explicit; bracket must agree with the IANA zone)\n * 2. UTC or fixed-offset Instant\n * e.g. `\"2024-01-01T00:00:00Z\"`, `\"2024-01-01T00:00:00+02:00\"`\n * 3. Plain date or datetime (no offset, `Z`, or IANA bracket), interpreted as UTC\n * e.g. `\"2024-01-01\"`, `\"2024-01-01T14:30:00\"`, `\"2024-01-01T14:30:00.500\"`\n *\n * Strings with a time component that lack `Z`, an offset, or an IANA bracket are\n * parsed as UTC wall-clock time (same semantics as Neo4j `LocalDateTime`).\n */\nexport function parseDateString(s: string): number | null {\n // RFC 9557 / ZonedDateTime with IANA bracket notation\n try {\n return Temporal.ZonedDateTime.from(s).epochMilliseconds;\n } catch {\n /* empty */\n }\n\n // UTC or fixed-offset datetime (no IANA name)\n try {\n return Temporal.Instant.from(s).epochMilliseconds;\n } catch {\n /* empty */\n }\n\n // Plain datetime — interpret as UTC.\n // Also covers date-only strings like \"2024-01-01\" (PlainDateTime.from parses\n // them as midnight), so a separate PlainDate path is not needed.\n try {\n return Temporal.PlainDateTime.from(s).toZonedDateTime('UTC')\n .epochMilliseconds;\n } catch {\n /* empty */\n }\n\n return null;\n}\n"]}
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
/*
|
|
2
|
+
* AUTO-GENERATED FILE — DO NOT EDIT.
|
|
3
|
+
* Source of truth: packages/style-rules/src/
|
|
4
|
+
* Regenerate with `pnpm generate:shared` (runs automatically at build/dev/install).
|
|
5
|
+
*/
|
|
6
|
+
/**
|
|
7
|
+
*
|
|
8
|
+
* Copyright (c) "Neo4j"
|
|
9
|
+
* Neo4j Sweden AB [http://neo4j.com]
|
|
10
|
+
*
|
|
11
|
+
* This file is part of Neo4j.
|
|
12
|
+
*
|
|
13
|
+
* Neo4j is free software: you can redistribute it and/or modify
|
|
14
|
+
* it under the terms of the GNU General Public License as published by
|
|
15
|
+
* the Free Software Foundation, either version 3 of the License, or
|
|
16
|
+
* (at your option) any later version.
|
|
17
|
+
*
|
|
18
|
+
* This program is distributed in the hope that it will be useful,
|
|
19
|
+
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
20
|
+
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
21
|
+
* GNU General Public License for more details.
|
|
22
|
+
*
|
|
23
|
+
* You should have received a copy of the GNU General Public License
|
|
24
|
+
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
|
25
|
+
*/
|
|
26
|
+
export { getWeight, lerpColor } from './color-utils';
|
|
27
|
+
export { parseDateString, parseTimeString } from './date-utils';
|
|
28
|
+
export { DatetimeLiteralSchema, TimeLiteralSchema } from './literal-schemas';
|
|
29
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../../../src/_generated/style-rules/index.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAEH;;;;;;;;;;;;;;;;;;;GAmBG;AAEH,OAAO,EAAE,SAAS,EAAE,SAAS,EAAE,MAAM,eAAe,CAAC;AACrD,OAAO,EAAE,eAAe,EAAE,eAAe,EAAE,MAAM,cAAc,CAAC;AAChE,OAAO,EAAE,qBAAqB,EAAE,iBAAiB,EAAE,MAAM,mBAAmB,CAAC","sourcesContent":["/*\n * AUTO-GENERATED FILE — DO NOT EDIT.\n * Source of truth: packages/style-rules/src/\n * Regenerate with `pnpm generate:shared` (runs automatically at build/dev/install).\n */\n\n/**\n *\n * Copyright (c) \"Neo4j\"\n * Neo4j Sweden AB [http://neo4j.com]\n *\n * This file is part of Neo4j.\n *\n * Neo4j is free software: you can redistribute it and/or modify\n * it under the terms of the GNU General Public License as published by\n * the Free Software Foundation, either version 3 of the License, or\n * (at your option) any later version.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program. If not, see <http://www.gnu.org/licenses/>.\n */\n\nexport { getWeight, lerpColor } from './color-utils';\nexport { parseDateString, parseTimeString } from './date-utils';\nexport { DatetimeLiteralSchema, TimeLiteralSchema } from './literal-schemas';\nexport type { DatetimeLiteral, TimeLiteral } from './literal-schemas';\n"]}
|
|
@@ -0,0 +1,61 @@
|
|
|
1
|
+
/*
|
|
2
|
+
* AUTO-GENERATED FILE — DO NOT EDIT.
|
|
3
|
+
* Source of truth: packages/style-rules/src/
|
|
4
|
+
* Regenerate with `pnpm generate:shared` (runs automatically at build/dev/install).
|
|
5
|
+
*/
|
|
6
|
+
/**
|
|
7
|
+
*
|
|
8
|
+
* Copyright (c) "Neo4j"
|
|
9
|
+
* Neo4j Sweden AB [http://neo4j.com]
|
|
10
|
+
*
|
|
11
|
+
* This file is part of Neo4j.
|
|
12
|
+
*
|
|
13
|
+
* Neo4j is free software: you can redistribute it and/or modify
|
|
14
|
+
* it under the terms of the GNU General Public License as published by
|
|
15
|
+
* the Free Software Foundation, either version 3 of the License, or
|
|
16
|
+
* (at your option) any later version.
|
|
17
|
+
*
|
|
18
|
+
* This program is distributed in the hope that it will be useful,
|
|
19
|
+
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
20
|
+
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
21
|
+
* GNU General Public License for more details.
|
|
22
|
+
*
|
|
23
|
+
* You should have received a copy of the GNU General Public License
|
|
24
|
+
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
|
25
|
+
*/
|
|
26
|
+
import { z } from 'zod';
|
|
27
|
+
import { parseDateString, parseTimeString } from './date-utils';
|
|
28
|
+
/**
|
|
29
|
+
* An ISO 8601 or RFC 9557 datetime literal that resolves to a Unix millisecond
|
|
30
|
+
* timestamp at evaluation time. Supported formats:
|
|
31
|
+
* - RFC 9557 with IANA timezone: `"2024-06-15T14:00:00[Europe/Stockholm]"` (offset
|
|
32
|
+
* inferred from the named zone, DST-aware) or `"2024-06-15T14:00:00+02:00[Europe/Stockholm]"`
|
|
33
|
+
* (offset explicit)
|
|
34
|
+
* - UTC or offset datetime: `"2024-01-01T00:00:00Z"`, `"2024-01-01T00:00:00+02:00"`
|
|
35
|
+
* - Plain datetime (treated as UTC): `"2024-01-01T14:30:00"`, `"2024-01-01T14:30:00.500"`
|
|
36
|
+
* - Date-only (treated as UTC midnight): `"2024-01-01"`
|
|
37
|
+
*/
|
|
38
|
+
export const DatetimeLiteralSchema = z.object({
|
|
39
|
+
datetime: z.string().refine((s) => parseDateString(s) !== null, {
|
|
40
|
+
message: 'datetime must be a valid ISO 8601 / RFC 9557 date or datetime string',
|
|
41
|
+
}),
|
|
42
|
+
});
|
|
43
|
+
/**
|
|
44
|
+
* An ISO 8601 time literal that resolves to milliseconds since UTC midnight
|
|
45
|
+
* at evaluation time. Supported formats:
|
|
46
|
+
* - Local time (treated as UTC): `"14:30:00"`, `"14:30:00.500"`
|
|
47
|
+
* - UTC time: `"14:30:00Z"` — identical to local form
|
|
48
|
+
* - Offset time (UTC-normalised): `"14:30:00+02:00"` → 45,000,000 ms (12:30 UTC)
|
|
49
|
+
*
|
|
50
|
+
* IANA timezone brackets (e.g. `[Europe/Stockholm]`) are **not** accepted — a
|
|
51
|
+
* time-of-day value has no calendar date so DST cannot be resolved. Use
|
|
52
|
+
* `{ datetime }` literals for timezone-aware instants.
|
|
53
|
+
*
|
|
54
|
+
* Full datetime strings (containing `T`) are rejected.
|
|
55
|
+
*/
|
|
56
|
+
export const TimeLiteralSchema = z.object({
|
|
57
|
+
time: z.string().refine((s) => parseTimeString(s) !== null, {
|
|
58
|
+
message: 'time must be a valid ISO 8601 time string (e.g. "14:30:00" or "14:30:00+02:00")',
|
|
59
|
+
}),
|
|
60
|
+
});
|
|
61
|
+
//# sourceMappingURL=literal-schemas.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"literal-schemas.js","sourceRoot":"","sources":["../../../../src/_generated/style-rules/literal-schemas.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAEH;;;;;;;;;;;;;;;;;;;GAmBG;AAEH,OAAO,EAAE,CAAC,EAAE,MAAM,KAAK,CAAC;AAExB,OAAO,EAAE,eAAe,EAAE,eAAe,EAAE,MAAM,cAAc,CAAC;AAEhE;;;;;;;;;GASG;AACH,MAAM,CAAC,MAAM,qBAAqB,GAAG,CAAC,CAAC,MAAM,CAAC;IAC5C,QAAQ,EAAE,CAAC,CAAC,MAAM,EAAE,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,eAAe,CAAC,CAAC,CAAC,KAAK,IAAI,EAAE;QAC9D,OAAO,EACL,sEAAsE;KACzE,CAAC;CACH,CAAC,CAAC;AAGH;;;;;;;;;;;;GAYG;AACH,MAAM,CAAC,MAAM,iBAAiB,GAAG,CAAC,CAAC,MAAM,CAAC;IACxC,IAAI,EAAE,CAAC,CAAC,MAAM,EAAE,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,eAAe,CAAC,CAAC,CAAC,KAAK,IAAI,EAAE;QAC1D,OAAO,EACL,iFAAiF;KACpF,CAAC;CACH,CAAC,CAAC","sourcesContent":["/*\n * AUTO-GENERATED FILE — DO NOT EDIT.\n * Source of truth: packages/style-rules/src/\n * Regenerate with `pnpm generate:shared` (runs automatically at build/dev/install).\n */\n\n/**\n *\n * Copyright (c) \"Neo4j\"\n * Neo4j Sweden AB [http://neo4j.com]\n *\n * This file is part of Neo4j.\n *\n * Neo4j is free software: you can redistribute it and/or modify\n * it under the terms of the GNU General Public License as published by\n * the Free Software Foundation, either version 3 of the License, or\n * (at your option) any later version.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program. If not, see <http://www.gnu.org/licenses/>.\n */\n\nimport { z } from 'zod';\n\nimport { parseDateString, parseTimeString } from './date-utils';\n\n/**\n * An ISO 8601 or RFC 9557 datetime literal that resolves to a Unix millisecond\n * timestamp at evaluation time. Supported formats:\n * - RFC 9557 with IANA timezone: `\"2024-06-15T14:00:00[Europe/Stockholm]\"` (offset\n * inferred from the named zone, DST-aware) or `\"2024-06-15T14:00:00+02:00[Europe/Stockholm]\"`\n * (offset explicit)\n * - UTC or offset datetime: `\"2024-01-01T00:00:00Z\"`, `\"2024-01-01T00:00:00+02:00\"`\n * - Plain datetime (treated as UTC): `\"2024-01-01T14:30:00\"`, `\"2024-01-01T14:30:00.500\"`\n * - Date-only (treated as UTC midnight): `\"2024-01-01\"`\n */\nexport const DatetimeLiteralSchema = z.object({\n datetime: z.string().refine((s) => parseDateString(s) !== null, {\n message:\n 'datetime must be a valid ISO 8601 / RFC 9557 date or datetime string',\n }),\n});\nexport type DatetimeLiteral = z.infer<typeof DatetimeLiteralSchema>;\n\n/**\n * An ISO 8601 time literal that resolves to milliseconds since UTC midnight\n * at evaluation time. Supported formats:\n * - Local time (treated as UTC): `\"14:30:00\"`, `\"14:30:00.500\"`\n * - UTC time: `\"14:30:00Z\"` — identical to local form\n * - Offset time (UTC-normalised): `\"14:30:00+02:00\"` → 45,000,000 ms (12:30 UTC)\n *\n * IANA timezone brackets (e.g. `[Europe/Stockholm]`) are **not** accepted — a\n * time-of-day value has no calendar date so DST cannot be resolved. Use\n * `{ datetime }` literals for timezone-aware instants.\n *\n * Full datetime strings (containing `T`) are rejected.\n */\nexport const TimeLiteralSchema = z.object({\n time: z.string().refine((s) => parseTimeString(s) !== null, {\n message:\n 'time must be a valid ISO 8601 time string (e.g. \"14:30:00\" or \"14:30:00+02:00\")',\n }),\n});\nexport type TimeLiteral = z.infer<typeof TimeLiteralSchema>;\n"]}
|
|
@@ -0,0 +1,284 @@
|
|
|
1
|
+
import { jsx as _jsx } from "react/jsx-runtime";
|
|
2
|
+
/**
|
|
3
|
+
*
|
|
4
|
+
* Copyright (c) "Neo4j"
|
|
5
|
+
* Neo4j Sweden AB [http://neo4j.com]
|
|
6
|
+
*
|
|
7
|
+
* This file is part of Neo4j.
|
|
8
|
+
*
|
|
9
|
+
* Neo4j is free software: you can redistribute it and/or modify
|
|
10
|
+
* it under the terms of the GNU General Public License as published by
|
|
11
|
+
* the Free Software Foundation, either version 3 of the License, or
|
|
12
|
+
* (at your option) any later version.
|
|
13
|
+
*
|
|
14
|
+
* This program is distributed in the hope that it will be useful,
|
|
15
|
+
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
16
|
+
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
17
|
+
* GNU General Public License for more details.
|
|
18
|
+
*
|
|
19
|
+
* You should have received a copy of the GNU General Public License
|
|
20
|
+
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
|
21
|
+
*/
|
|
22
|
+
import '@neo4j-ndl/base/lib/neo4j-ds-styles.css';
|
|
23
|
+
import { DataGrid } from '@neo4j-ndl/react';
|
|
24
|
+
import { createColumnHelper, getCoreRowModel, getPaginationRowModel, getSortedRowModel, useReactTable, } from '@tanstack/react-table';
|
|
25
|
+
const data = [
|
|
26
|
+
// ── Past events (before start of 2026-06-25 in Stockholm / CEST) ──────────
|
|
27
|
+
{
|
|
28
|
+
event: 'Quarterly review',
|
|
29
|
+
// 09:00 Stockholm CEST = 07:00 UTC
|
|
30
|
+
scheduledDate: new Date('2026-06-10T09:00:00+02:00'),
|
|
31
|
+
scheduledTimeMs: 7 * 3600000,
|
|
32
|
+
localTimeDisplay: '09:00 CEST (+02:00)',
|
|
33
|
+
status: 'confirmed',
|
|
34
|
+
},
|
|
35
|
+
{
|
|
36
|
+
event: 'Security audit',
|
|
37
|
+
// 07:30 London BST (+01:00) = 06:30 UTC — before Stockholm opens
|
|
38
|
+
scheduledDate: new Date('2026-06-18T07:30:00+01:00'),
|
|
39
|
+
scheduledTimeMs: 6 * 3600000 + 30 * 60000,
|
|
40
|
+
localTimeDisplay: '07:30 BST (+01:00)',
|
|
41
|
+
status: 'delayed',
|
|
42
|
+
},
|
|
43
|
+
// ── Today (2026-06-25 in Stockholm / CEST) ─────────────────────────────────
|
|
44
|
+
{
|
|
45
|
+
event: 'Customer demo',
|
|
46
|
+
// 09:00 New York EDT (-04:00) = 13:00 UTC
|
|
47
|
+
scheduledDate: new Date('2026-06-25T09:00:00-04:00'),
|
|
48
|
+
scheduledTimeMs: 13 * 3600000,
|
|
49
|
+
localTimeDisplay: '09:00 EDT (-04:00)',
|
|
50
|
+
status: 'confirmed',
|
|
51
|
+
},
|
|
52
|
+
{
|
|
53
|
+
event: 'Platform migration',
|
|
54
|
+
// 22:00 Stockholm CEST (+02:00) = 20:00 UTC — after Stockholm closes
|
|
55
|
+
scheduledDate: new Date('2026-06-25T22:00:00+02:00'),
|
|
56
|
+
scheduledTimeMs: 20 * 3600000,
|
|
57
|
+
localTimeDisplay: '22:00 CEST (+02:00)',
|
|
58
|
+
status: 'confirmed',
|
|
59
|
+
},
|
|
60
|
+
// ── Near future (up to and including 2026-07-14 in Stockholm) ─────────────
|
|
61
|
+
{
|
|
62
|
+
event: 'Board presentation',
|
|
63
|
+
// 10:00 Singapore SGT (+08:00) = 02:00 UTC — before Stockholm opens
|
|
64
|
+
scheduledDate: new Date('2026-07-02T10:00:00+08:00'),
|
|
65
|
+
scheduledTimeMs: 2 * 3600000,
|
|
66
|
+
localTimeDisplay: '10:00 SGT (+08:00)',
|
|
67
|
+
status: 'confirmed',
|
|
68
|
+
},
|
|
69
|
+
{
|
|
70
|
+
event: 'Partner onboarding',
|
|
71
|
+
// 13:15 Paris CEST (+02:00) = 11:15 UTC
|
|
72
|
+
scheduledDate: new Date('2026-07-08T13:15:00+02:00'),
|
|
73
|
+
scheduledTimeMs: 11 * 3600000 + 15 * 60000,
|
|
74
|
+
localTimeDisplay: '13:15 CEST (+02:00)',
|
|
75
|
+
status: 'cancelled',
|
|
76
|
+
},
|
|
77
|
+
// ── Far future (after 2026-07-15T00:00 Stockholm / CEST = 2026-07-14T22:00Z)
|
|
78
|
+
{
|
|
79
|
+
event: 'Architecture summit',
|
|
80
|
+
// 08:00 Amsterdam CEST (+02:00) = 06:00 UTC.
|
|
81
|
+
// Although the calendar date is "July 15", 08:00 CEST is still within the
|
|
82
|
+
// same UTC day as July 14 22:00Z, so it crosses the far-future boundary.
|
|
83
|
+
scheduledDate: new Date('2026-07-15T08:00:00+02:00'),
|
|
84
|
+
scheduledTimeMs: 6 * 3600000,
|
|
85
|
+
localTimeDisplay: '08:00 CEST (+02:00)',
|
|
86
|
+
status: 'confirmed',
|
|
87
|
+
},
|
|
88
|
+
{
|
|
89
|
+
event: 'Annual conference',
|
|
90
|
+
// 09:00 San Francisco PDT (-07:00) = 16:00 UTC — after Stockholm closes
|
|
91
|
+
scheduledDate: new Date('2026-08-03T09:00:00-07:00'),
|
|
92
|
+
scheduledTimeMs: 16 * 3600000,
|
|
93
|
+
localTimeDisplay: '09:00 PDT (-07:00)',
|
|
94
|
+
status: 'confirmed',
|
|
95
|
+
},
|
|
96
|
+
{
|
|
97
|
+
event: 'Year-end planning',
|
|
98
|
+
// 09:00 Tokyo JST (+09:00) = 00:00 UTC — midnight, well before Stockholm opens
|
|
99
|
+
scheduledDate: new Date('2026-11-20T09:00:00+09:00'),
|
|
100
|
+
scheduledTimeMs: 0,
|
|
101
|
+
localTimeDisplay: '09:00 JST (+09:00)',
|
|
102
|
+
status: 'confirmed',
|
|
103
|
+
},
|
|
104
|
+
];
|
|
105
|
+
/**
|
|
106
|
+
* All date and time boundaries are anchored to Stockholm in June–July 2026.
|
|
107
|
+
* Date literals use RFC 9557 IANA bracket notation — the UTC offset is inferred
|
|
108
|
+
* from the named zone (CEST = +02:00 in this period); writing `+02:00` explicitly
|
|
109
|
+
* is optional. Time literals use UTC-offset notation.
|
|
110
|
+
*
|
|
111
|
+
* "Today" from a Stockholm perspective:
|
|
112
|
+
* 2026-06-25T00:00:00[Europe/Stockholm] = 2026-06-24T22:00:00Z
|
|
113
|
+
* 2026-06-26T00:00:00[Europe/Stockholm] = 2026-06-25T22:00:00Z
|
|
114
|
+
*
|
|
115
|
+
* "Far future" threshold:
|
|
116
|
+
* 2026-07-15T00:00:00[Europe/Stockholm] = 2026-07-14T22:00:00Z
|
|
117
|
+
*
|
|
118
|
+
* Business hours (Stockholm):
|
|
119
|
+
* { time: '09:00:00+02:00' } resolves to 07:00 UTC (25 200 000 ms)
|
|
120
|
+
* { time: '17:00:00+02:00' } resolves to 15:00 UTC (54 000 000 ms)
|
|
121
|
+
*/
|
|
122
|
+
const styleRules = [
|
|
123
|
+
// Past events — entire row in muted red
|
|
124
|
+
{
|
|
125
|
+
apply: {
|
|
126
|
+
color: { value: '#fee2e2' },
|
|
127
|
+
textColor: { value: '#7f1d1d' },
|
|
128
|
+
},
|
|
129
|
+
column: null,
|
|
130
|
+
priority: 1,
|
|
131
|
+
where: {
|
|
132
|
+
lessThan: [
|
|
133
|
+
{ column: 'scheduledDate' },
|
|
134
|
+
{ datetime: '2026-06-25T00:00:00[Europe/Stockholm]' },
|
|
135
|
+
],
|
|
136
|
+
},
|
|
137
|
+
},
|
|
138
|
+
// Today (in Stockholm timezone) — entire row in amber
|
|
139
|
+
{
|
|
140
|
+
apply: {
|
|
141
|
+
color: { value: '#fef9c3' },
|
|
142
|
+
textColor: { value: '#713f12' },
|
|
143
|
+
},
|
|
144
|
+
column: null,
|
|
145
|
+
priority: 1,
|
|
146
|
+
where: {
|
|
147
|
+
and: [
|
|
148
|
+
{
|
|
149
|
+
greaterThanOrEqual: [
|
|
150
|
+
{ column: 'scheduledDate' },
|
|
151
|
+
{ datetime: '2026-06-25T00:00:00[Europe/Stockholm]' },
|
|
152
|
+
],
|
|
153
|
+
},
|
|
154
|
+
{
|
|
155
|
+
lessThan: [
|
|
156
|
+
{ column: 'scheduledDate' },
|
|
157
|
+
{ datetime: '2026-06-26T00:00:00[Europe/Stockholm]' },
|
|
158
|
+
],
|
|
159
|
+
},
|
|
160
|
+
],
|
|
161
|
+
},
|
|
162
|
+
},
|
|
163
|
+
// Far future (after 2026-07-15 midnight Stockholm time) — entire row in green
|
|
164
|
+
{
|
|
165
|
+
apply: {
|
|
166
|
+
color: { value: '#dcfce7' },
|
|
167
|
+
textColor: { value: '#14532d' },
|
|
168
|
+
},
|
|
169
|
+
column: null,
|
|
170
|
+
priority: 1,
|
|
171
|
+
where: {
|
|
172
|
+
greaterThanOrEqual: [
|
|
173
|
+
{ column: 'scheduledDate' },
|
|
174
|
+
{ datetime: '2026-07-15T00:00:00[Europe/Stockholm]' },
|
|
175
|
+
],
|
|
176
|
+
},
|
|
177
|
+
},
|
|
178
|
+
// Outside Stockholm business hours (before 09:00 CEST or from 17:00 CEST) —
|
|
179
|
+
// time cell in orange. The { time: "..." } literals carry an offset so the
|
|
180
|
+
// engine normalises them to UTC before comparing against scheduledTimeMs.
|
|
181
|
+
{
|
|
182
|
+
apply: {
|
|
183
|
+
color: { value: '#ffedd5' },
|
|
184
|
+
textColor: { value: '#7c2d12' },
|
|
185
|
+
},
|
|
186
|
+
column: 'scheduledTimeMs',
|
|
187
|
+
priority: 2,
|
|
188
|
+
where: {
|
|
189
|
+
or: [
|
|
190
|
+
{
|
|
191
|
+
lessThan: [{ column: 'scheduledTimeMs' }, { time: '09:00:00+02:00' }],
|
|
192
|
+
},
|
|
193
|
+
{
|
|
194
|
+
greaterThanOrEqual: [
|
|
195
|
+
{ column: 'scheduledTimeMs' },
|
|
196
|
+
{ time: '17:00:00+02:00' },
|
|
197
|
+
],
|
|
198
|
+
},
|
|
199
|
+
],
|
|
200
|
+
},
|
|
201
|
+
},
|
|
202
|
+
// Cancelled events — all cells grayed out at highest priority
|
|
203
|
+
{
|
|
204
|
+
apply: {
|
|
205
|
+
color: { value: '#f3f4f6' },
|
|
206
|
+
textColor: { value: '#9ca3af' },
|
|
207
|
+
},
|
|
208
|
+
column: null,
|
|
209
|
+
priority: 5,
|
|
210
|
+
where: { equal: [{ column: 'status' }, 'cancelled'] },
|
|
211
|
+
},
|
|
212
|
+
];
|
|
213
|
+
const Component = () => {
|
|
214
|
+
const columnHelper = createColumnHelper();
|
|
215
|
+
const columns = [
|
|
216
|
+
columnHelper.accessor('event', {
|
|
217
|
+
cell: (info) => info.getValue(),
|
|
218
|
+
header: () => 'Event',
|
|
219
|
+
minSize: 180,
|
|
220
|
+
size: 220,
|
|
221
|
+
}),
|
|
222
|
+
columnHelper.accessor('scheduledDate', {
|
|
223
|
+
cell: (info) => info.getValue().toLocaleDateString('en-GB', {
|
|
224
|
+
day: 'numeric',
|
|
225
|
+
month: 'short',
|
|
226
|
+
timeZone: 'Europe/Stockholm',
|
|
227
|
+
year: 'numeric',
|
|
228
|
+
}),
|
|
229
|
+
header: () => 'Date (Stockholm)',
|
|
230
|
+
minSize: 150,
|
|
231
|
+
size: 170,
|
|
232
|
+
}),
|
|
233
|
+
columnHelper.accessor('localTimeDisplay', {
|
|
234
|
+
cell: (info) => info.getValue(),
|
|
235
|
+
header: () => 'Local time',
|
|
236
|
+
minSize: 160,
|
|
237
|
+
size: 180,
|
|
238
|
+
}),
|
|
239
|
+
columnHelper.accessor('scheduledTimeMs', {
|
|
240
|
+
cell: (info) => {
|
|
241
|
+
const ms = info.getValue();
|
|
242
|
+
const h = Math.floor(ms / 3600000)
|
|
243
|
+
.toString()
|
|
244
|
+
.padStart(2, '0');
|
|
245
|
+
const m = Math.floor((ms % 3600000) / 60000)
|
|
246
|
+
.toString()
|
|
247
|
+
.padStart(2, '0');
|
|
248
|
+
return `${h}:${m} UTC`;
|
|
249
|
+
},
|
|
250
|
+
header: () => 'Time (UTC)',
|
|
251
|
+
minSize: 110,
|
|
252
|
+
size: 130,
|
|
253
|
+
}),
|
|
254
|
+
columnHelper.accessor('status', {
|
|
255
|
+
cell: (info) => info.getValue(),
|
|
256
|
+
header: () => 'Status',
|
|
257
|
+
minSize: 100,
|
|
258
|
+
size: 120,
|
|
259
|
+
}),
|
|
260
|
+
];
|
|
261
|
+
const table = useReactTable({
|
|
262
|
+
columnResizeMode: 'onChange',
|
|
263
|
+
columns,
|
|
264
|
+
data,
|
|
265
|
+
defaultColumn: {
|
|
266
|
+
maxSize: 800,
|
|
267
|
+
minSize: 80,
|
|
268
|
+
},
|
|
269
|
+
enableSorting: true,
|
|
270
|
+
getCoreRowModel: getCoreRowModel(),
|
|
271
|
+
getPaginationRowModel: getPaginationRowModel(),
|
|
272
|
+
getSortedRowModel: getSortedRowModel(),
|
|
273
|
+
initialState: {
|
|
274
|
+
pagination: { pageSize: 10 },
|
|
275
|
+
},
|
|
276
|
+
});
|
|
277
|
+
return (_jsx("div", { className: "n-w-full n-bg-light-neutral-text-weakest", children: _jsx(DataGrid, { isResizable: false, isKeyboardNavigable: false, tableInstance: table, styleRules: styleRules, styling: {
|
|
278
|
+
borderStyle: 'all-sides',
|
|
279
|
+
hasHoverEffects: true,
|
|
280
|
+
hasZebraStriping: false,
|
|
281
|
+
} }) }));
|
|
282
|
+
};
|
|
283
|
+
export default Component;
|
|
284
|
+
//# sourceMappingURL=datagrid-rule-based-styling-datetime.story.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"datagrid-rule-based-styling-datetime.story.js","sourceRoot":"","sources":["../../../../src/data-grid/stories/datagrid-rule-based-styling-datetime.story.tsx"],"names":[],"mappings":"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","sourcesContent":["/**\n *\n * Copyright (c) \"Neo4j\"\n * Neo4j Sweden AB [http://neo4j.com]\n *\n * This file is part of Neo4j.\n *\n * Neo4j is free software: you can redistribute it and/or modify\n * it under the terms of the GNU General Public License as published by\n * the Free Software Foundation, either version 3 of the License, or\n * (at your option) any later version.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program. If not, see <http://www.gnu.org/licenses/>.\n */\n\nimport '@neo4j-ndl/base/lib/neo4j-ds-styles.css';\n\nimport { DataGrid } from '@neo4j-ndl/react';\nimport {\n createColumnHelper,\n getCoreRowModel,\n getPaginationRowModel,\n getSortedRowModel,\n useReactTable,\n} from '@tanstack/react-table';\n\nimport { type DataGridStyleRule } from '../style-rules/types';\n\ntype EventRow = {\n event: string;\n /**\n * JS Date coerced from the event's local ISO string. Natively converted to\n * Unix ms by the engine and compared against { datetime: \"...\" } literals.\n */\n scheduledDate: Date;\n /**\n * UTC milliseconds since midnight. Compared against { time: \"...\" } literals\n * that are defined in Stockholm / CEST (+02:00) time — the engine normalises\n * both sides to UTC before comparing.\n */\n scheduledTimeMs: number;\n /** Human-readable local time shown in the cell, e.g. \"09:00 CEST (+02:00)\". */\n localTimeDisplay: string;\n status: 'confirmed' | 'delayed' | 'cancelled';\n};\n\nconst data: EventRow[] = [\n // ── Past events (before start of 2026-06-25 in Stockholm / CEST) ──────────\n {\n event: 'Quarterly review',\n // 09:00 Stockholm CEST = 07:00 UTC\n scheduledDate: new Date('2026-06-10T09:00:00+02:00'),\n scheduledTimeMs: 7 * 3_600_000,\n localTimeDisplay: '09:00 CEST (+02:00)',\n status: 'confirmed',\n },\n {\n event: 'Security audit',\n // 07:30 London BST (+01:00) = 06:30 UTC — before Stockholm opens\n scheduledDate: new Date('2026-06-18T07:30:00+01:00'),\n scheduledTimeMs: 6 * 3_600_000 + 30 * 60_000,\n localTimeDisplay: '07:30 BST (+01:00)',\n status: 'delayed',\n },\n // ── Today (2026-06-25 in Stockholm / CEST) ─────────────────────────────────\n {\n event: 'Customer demo',\n // 09:00 New York EDT (-04:00) = 13:00 UTC\n scheduledDate: new Date('2026-06-25T09:00:00-04:00'),\n scheduledTimeMs: 13 * 3_600_000,\n localTimeDisplay: '09:00 EDT (-04:00)',\n status: 'confirmed',\n },\n {\n event: 'Platform migration',\n // 22:00 Stockholm CEST (+02:00) = 20:00 UTC — after Stockholm closes\n scheduledDate: new Date('2026-06-25T22:00:00+02:00'),\n scheduledTimeMs: 20 * 3_600_000,\n localTimeDisplay: '22:00 CEST (+02:00)',\n status: 'confirmed',\n },\n // ── Near future (up to and including 2026-07-14 in Stockholm) ─────────────\n {\n event: 'Board presentation',\n // 10:00 Singapore SGT (+08:00) = 02:00 UTC — before Stockholm opens\n scheduledDate: new Date('2026-07-02T10:00:00+08:00'),\n scheduledTimeMs: 2 * 3_600_000,\n localTimeDisplay: '10:00 SGT (+08:00)',\n status: 'confirmed',\n },\n {\n event: 'Partner onboarding',\n // 13:15 Paris CEST (+02:00) = 11:15 UTC\n scheduledDate: new Date('2026-07-08T13:15:00+02:00'),\n scheduledTimeMs: 11 * 3_600_000 + 15 * 60_000,\n localTimeDisplay: '13:15 CEST (+02:00)',\n status: 'cancelled',\n },\n // ── Far future (after 2026-07-15T00:00 Stockholm / CEST = 2026-07-14T22:00Z)\n {\n event: 'Architecture summit',\n // 08:00 Amsterdam CEST (+02:00) = 06:00 UTC.\n // Although the calendar date is \"July 15\", 08:00 CEST is still within the\n // same UTC day as July 14 22:00Z, so it crosses the far-future boundary.\n scheduledDate: new Date('2026-07-15T08:00:00+02:00'),\n scheduledTimeMs: 6 * 3_600_000,\n localTimeDisplay: '08:00 CEST (+02:00)',\n status: 'confirmed',\n },\n {\n event: 'Annual conference',\n // 09:00 San Francisco PDT (-07:00) = 16:00 UTC — after Stockholm closes\n scheduledDate: new Date('2026-08-03T09:00:00-07:00'),\n scheduledTimeMs: 16 * 3_600_000,\n localTimeDisplay: '09:00 PDT (-07:00)',\n status: 'confirmed',\n },\n {\n event: 'Year-end planning',\n // 09:00 Tokyo JST (+09:00) = 00:00 UTC — midnight, well before Stockholm opens\n scheduledDate: new Date('2026-11-20T09:00:00+09:00'),\n scheduledTimeMs: 0,\n localTimeDisplay: '09:00 JST (+09:00)',\n status: 'confirmed',\n },\n];\n\n/**\n * All date and time boundaries are anchored to Stockholm in June–July 2026.\n * Date literals use RFC 9557 IANA bracket notation — the UTC offset is inferred\n * from the named zone (CEST = +02:00 in this period); writing `+02:00` explicitly\n * is optional. Time literals use UTC-offset notation.\n *\n * \"Today\" from a Stockholm perspective:\n * 2026-06-25T00:00:00[Europe/Stockholm] = 2026-06-24T22:00:00Z\n * 2026-06-26T00:00:00[Europe/Stockholm] = 2026-06-25T22:00:00Z\n *\n * \"Far future\" threshold:\n * 2026-07-15T00:00:00[Europe/Stockholm] = 2026-07-14T22:00:00Z\n *\n * Business hours (Stockholm):\n * { time: '09:00:00+02:00' } resolves to 07:00 UTC (25 200 000 ms)\n * { time: '17:00:00+02:00' } resolves to 15:00 UTC (54 000 000 ms)\n */\nconst styleRules: DataGridStyleRule[] = [\n // Past events — entire row in muted red\n {\n apply: {\n color: { value: '#fee2e2' },\n textColor: { value: '#7f1d1d' },\n },\n column: null,\n priority: 1,\n where: {\n lessThan: [\n { column: 'scheduledDate' },\n { datetime: '2026-06-25T00:00:00[Europe/Stockholm]' },\n ],\n },\n },\n // Today (in Stockholm timezone) — entire row in amber\n {\n apply: {\n color: { value: '#fef9c3' },\n textColor: { value: '#713f12' },\n },\n column: null,\n priority: 1,\n where: {\n and: [\n {\n greaterThanOrEqual: [\n { column: 'scheduledDate' },\n { datetime: '2026-06-25T00:00:00[Europe/Stockholm]' },\n ],\n },\n {\n lessThan: [\n { column: 'scheduledDate' },\n { datetime: '2026-06-26T00:00:00[Europe/Stockholm]' },\n ],\n },\n ],\n },\n },\n // Far future (after 2026-07-15 midnight Stockholm time) — entire row in green\n {\n apply: {\n color: { value: '#dcfce7' },\n textColor: { value: '#14532d' },\n },\n column: null,\n priority: 1,\n where: {\n greaterThanOrEqual: [\n { column: 'scheduledDate' },\n { datetime: '2026-07-15T00:00:00[Europe/Stockholm]' },\n ],\n },\n },\n // Outside Stockholm business hours (before 09:00 CEST or from 17:00 CEST) —\n // time cell in orange. The { time: \"...\" } literals carry an offset so the\n // engine normalises them to UTC before comparing against scheduledTimeMs.\n {\n apply: {\n color: { value: '#ffedd5' },\n textColor: { value: '#7c2d12' },\n },\n column: 'scheduledTimeMs',\n priority: 2,\n where: {\n or: [\n {\n lessThan: [{ column: 'scheduledTimeMs' }, { time: '09:00:00+02:00' }],\n },\n {\n greaterThanOrEqual: [\n { column: 'scheduledTimeMs' },\n { time: '17:00:00+02:00' },\n ],\n },\n ],\n },\n },\n // Cancelled events — all cells grayed out at highest priority\n {\n apply: {\n color: { value: '#f3f4f6' },\n textColor: { value: '#9ca3af' },\n },\n column: null,\n priority: 5,\n where: { equal: [{ column: 'status' }, 'cancelled'] },\n },\n];\n\nconst Component = () => {\n const columnHelper = createColumnHelper<EventRow>();\n\n const columns = [\n columnHelper.accessor('event', {\n cell: (info) => info.getValue(),\n header: () => 'Event',\n minSize: 180,\n size: 220,\n }),\n columnHelper.accessor('scheduledDate', {\n cell: (info) =>\n info.getValue().toLocaleDateString('en-GB', {\n day: 'numeric',\n month: 'short',\n timeZone: 'Europe/Stockholm',\n year: 'numeric',\n }),\n header: () => 'Date (Stockholm)',\n minSize: 150,\n size: 170,\n }),\n columnHelper.accessor('localTimeDisplay', {\n cell: (info) => info.getValue(),\n header: () => 'Local time',\n minSize: 160,\n size: 180,\n }),\n columnHelper.accessor('scheduledTimeMs', {\n cell: (info) => {\n const ms = info.getValue();\n const h = Math.floor(ms / 3_600_000)\n .toString()\n .padStart(2, '0');\n const m = Math.floor((ms % 3_600_000) / 60_000)\n .toString()\n .padStart(2, '0');\n return `${h}:${m} UTC`;\n },\n header: () => 'Time (UTC)',\n minSize: 110,\n size: 130,\n }),\n columnHelper.accessor('status', {\n cell: (info) => info.getValue(),\n header: () => 'Status',\n minSize: 100,\n size: 120,\n }),\n ];\n\n const table = useReactTable({\n columnResizeMode: 'onChange',\n columns,\n data,\n defaultColumn: {\n maxSize: 800,\n minSize: 80,\n },\n enableSorting: true,\n getCoreRowModel: getCoreRowModel(),\n getPaginationRowModel: getPaginationRowModel(),\n getSortedRowModel: getSortedRowModel(),\n initialState: {\n pagination: { pageSize: 10 },\n },\n });\n\n return (\n <div className=\"n-w-full n-bg-light-neutral-text-weakest\">\n <DataGrid\n isResizable={false}\n isKeyboardNavigable={false}\n tableInstance={table}\n styleRules={styleRules}\n styling={{\n borderStyle: 'all-sides',\n hasHoverEffects: true,\n hasZebraStriping: false,\n }}\n />\n </div>\n );\n};\n\nexport default Component;\n"]}
|
|
@@ -38,6 +38,7 @@ export { default as DataGridSingleSelectable } from './datagrid-single-selectabl
|
|
|
38
38
|
export { default as DataGridUsingEditableCells } from './datagrid-using-editable-cells.story';
|
|
39
39
|
export { default as DataGridRuleBasedStyling } from './datagrid-rule-based-styling.story';
|
|
40
40
|
export { default as DataGridCustomCellWithStyleRules } from './datagrid-custom-cell-with-style-rules.story';
|
|
41
|
+
export { default as DataGridRuleBasedStylingDateTime } from './datagrid-rule-based-styling-datetime.story';
|
|
41
42
|
import { removeLicenseHeader } from '../../_common/export-stories-utils';
|
|
42
43
|
import DataGridColumnFilteringSourceRaw from './datagrid-column-filtering.story?raw';
|
|
43
44
|
import DataGridCompactModeSourceRaw from './datagrid-compact-mode.story?raw';
|
|
@@ -52,6 +53,7 @@ import DataGridPinnedColumnsSourceRaw from './datagrid-pinned-columns.stories?ra
|
|
|
52
53
|
import DataGridPlaceholderStatesSourceRaw from './datagrid-placeholder-states.story?raw';
|
|
53
54
|
import DataGridResizableColumnSourceRaw from './datagrid-resizable-column.story?raw';
|
|
54
55
|
import DataGridRuleBasedStylingSourceRaw from './datagrid-rule-based-styling.story?raw';
|
|
56
|
+
import DataGridRuleBasedStylingDateTimeSourceRaw from './datagrid-rule-based-styling-datetime.story?raw';
|
|
55
57
|
import DataGridSearchableSourceRaw from './datagrid-search-and-filters.stories?raw';
|
|
56
58
|
import DataGridSelectableSourceRaw from './datagrid-selectable.story?raw';
|
|
57
59
|
import DataGridSimpleSourceRaw from './datagrid-simple.story?raw';
|
|
@@ -81,4 +83,5 @@ export const DataGridPinnedColumnsSource = removeLicenseHeader(DataGridPinnedCol
|
|
|
81
83
|
export const DataGridNoPaginationTableSource = removeLicenseHeader(DataGridNoPaginationTableRaw);
|
|
82
84
|
export const DataGridSingleSelectableSource = removeLicenseHeader(DataGridSingleSelectableSourceRaw);
|
|
83
85
|
export const DataGridUsingEditableCellsSource = removeLicenseHeader(DataGridUsingEditableCellsSourceRaw);
|
|
86
|
+
export const DataGridRuleBasedStylingDateTimeSource = removeLicenseHeader(DataGridRuleBasedStylingDateTimeSourceRaw);
|
|
84
87
|
//# sourceMappingURL=index.js.map
|