@newrelic/preflight 1.14.40 → 1.14.41
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/dist/dashboard/routes/api-handler.d.ts.map +1 -1
- package/dist/dashboard/routes/api-handler.js +46 -21
- package/dist/dashboard/routes/api-handler.js.map +1 -1
- package/dist/lib/date.d.ts +18 -7
- package/dist/lib/date.d.ts.map +1 -1
- package/dist/lib/date.js +154 -7
- package/dist/lib/date.js.map +1 -1
- package/dist/web/assets/{index-DmXPvYaO.js → index-C2qwK_PL.js} +3 -3
- package/dist/web/index.html +1 -1
- package/package.json +1 -1
package/dist/lib/date.js
CHANGED
|
@@ -8,26 +8,167 @@
|
|
|
8
8
|
* sides drew the day boundary at different moments and visible inconsistencies
|
|
9
9
|
* appeared (chart shows session active, sidebar filter drops it, etc.).
|
|
10
10
|
*
|
|
11
|
-
* These helpers operate in the host process's local timezone
|
|
12
|
-
* previous inline implementations.
|
|
13
|
-
* tz
|
|
11
|
+
* These helpers operate in the host process's own local timezone by default —
|
|
12
|
+
* same as the previous inline implementations. Each also accepts an optional
|
|
13
|
+
* trailing IANA `tz` (e.g. `"America/New_York"`); when given, Y/M/D is
|
|
14
|
+
* computed in that zone instead of the host's. Callers that need "today" to
|
|
15
|
+
* mean the *browser's* today (rather than the server process's) thread the
|
|
16
|
+
* browser's `Intl.DateTimeFormat().resolvedOptions().timeZone` through to
|
|
17
|
+
* these functions.
|
|
14
18
|
*/
|
|
19
|
+
// Intl.DateTimeFormat construction is measurably more expensive than
|
|
20
|
+
// formatToParts() itself, and the `history` branch of the activity-heatmap
|
|
21
|
+
// route calls into these helpers a few times per day boundary across up to
|
|
22
|
+
// 52 weeks in a single request on a single-threaded server. Today, the only
|
|
23
|
+
// caller that ever passes a `tz` (the activity-heatmap route) validates it
|
|
24
|
+
// against Intl.DateTimeFormat first — but these helpers themselves don't
|
|
25
|
+
// enforce that, so the cache key can't just be the raw `tz` string: distinct
|
|
26
|
+
// spellings of the same zone ('Asia/Kolkata', 'asia/kolkata', '+0530', ...)
|
|
27
|
+
// all construct successfully and would otherwise become distinct,
|
|
28
|
+
// never-evicted Map entries. Resolving each input to Intl's canonical zone
|
|
29
|
+
// name before touching the cache collapses those spelling variants onto one
|
|
30
|
+
// key, so the cache only grows with the number of *distinct* zones/offsets
|
|
31
|
+
// actually seen — not with every raw string a caller happens to send.
|
|
32
|
+
function canonicalTz(tz) {
|
|
33
|
+
return new Intl.DateTimeFormat('en-US', { timeZone: tz }).resolvedOptions().timeZone;
|
|
34
|
+
}
|
|
35
|
+
const ymdFormatterCache = new Map();
|
|
36
|
+
function ymdFormatterFor(tz) {
|
|
37
|
+
const canonical = canonicalTz(tz);
|
|
38
|
+
let formatter = ymdFormatterCache.get(canonical);
|
|
39
|
+
if (!formatter) {
|
|
40
|
+
formatter = new Intl.DateTimeFormat('en-US', {
|
|
41
|
+
timeZone: canonical,
|
|
42
|
+
year: 'numeric',
|
|
43
|
+
month: '2-digit',
|
|
44
|
+
day: '2-digit',
|
|
45
|
+
});
|
|
46
|
+
ymdFormatterCache.set(canonical, formatter);
|
|
47
|
+
}
|
|
48
|
+
return formatter;
|
|
49
|
+
}
|
|
50
|
+
const offsetFormatterCache = new Map();
|
|
51
|
+
function offsetFormatterFor(tz) {
|
|
52
|
+
const canonical = canonicalTz(tz);
|
|
53
|
+
let formatter = offsetFormatterCache.get(canonical);
|
|
54
|
+
if (!formatter) {
|
|
55
|
+
formatter = new Intl.DateTimeFormat('en-US', {
|
|
56
|
+
timeZone: canonical,
|
|
57
|
+
year: 'numeric',
|
|
58
|
+
month: '2-digit',
|
|
59
|
+
day: '2-digit',
|
|
60
|
+
hour: '2-digit',
|
|
61
|
+
minute: '2-digit',
|
|
62
|
+
second: '2-digit',
|
|
63
|
+
hour12: false,
|
|
64
|
+
});
|
|
65
|
+
offsetFormatterCache.set(canonical, formatter);
|
|
66
|
+
}
|
|
67
|
+
return formatter;
|
|
68
|
+
}
|
|
69
|
+
/**
|
|
70
|
+
* Y/M/D as observed in `tz` for the instant `ts`.
|
|
71
|
+
*/
|
|
72
|
+
function zonedYMD(ts, tz) {
|
|
73
|
+
const parts = ymdFormatterFor(tz).formatToParts(ts);
|
|
74
|
+
let year = 0;
|
|
75
|
+
let month = 0;
|
|
76
|
+
let day = 0;
|
|
77
|
+
for (const part of parts) {
|
|
78
|
+
if (part.type === 'year')
|
|
79
|
+
year = Number(part.value);
|
|
80
|
+
else if (part.type === 'month')
|
|
81
|
+
month = Number(part.value);
|
|
82
|
+
else if (part.type === 'day')
|
|
83
|
+
day = Number(part.value);
|
|
84
|
+
}
|
|
85
|
+
return { year, month, day };
|
|
86
|
+
}
|
|
87
|
+
/**
|
|
88
|
+
* `tz`'s UTC offset in ms (positive east of UTC) at the instant `ts`. Derived
|
|
89
|
+
* by reading `tz`'s wall-clock Y/M/D/H/M/S at `ts` and re-interpreting those
|
|
90
|
+
* same numbers as UTC — the gap between the two is the offset. This varies by
|
|
91
|
+
* date for zones that observe DST, so it must be read near the instant in
|
|
92
|
+
* question rather than assumed fixed.
|
|
93
|
+
*/
|
|
94
|
+
function zonedOffsetMs(ts, tz) {
|
|
95
|
+
const parts = offsetFormatterFor(tz).formatToParts(ts);
|
|
96
|
+
const values = {};
|
|
97
|
+
for (const part of parts) {
|
|
98
|
+
if (part.type !== 'literal')
|
|
99
|
+
values[part.type] = Number(part.value);
|
|
100
|
+
}
|
|
101
|
+
// Some ICU configurations render midnight as hour "24" under hour12: false.
|
|
102
|
+
const hour = values.hour === 24 ? 0 : values.hour;
|
|
103
|
+
const wallClockAsUtc = Date.UTC(values.year, values.month - 1, values.day, hour, values.minute, values.second);
|
|
104
|
+
return wallClockAsUtc - ts;
|
|
105
|
+
}
|
|
106
|
+
/**
|
|
107
|
+
* Epoch ms of local midnight for Y/M/D in `tz`. A first guess treats Y/M/D as
|
|
108
|
+
* if they were UTC, then that guess is corrected by `tz`'s actual offset at
|
|
109
|
+
* (approximately) that instant. Because the correction itself can move the
|
|
110
|
+
* candidate instant across a DST transition — landing on a moment where the
|
|
111
|
+
* offset is different from the one used to compute it — the offset is read
|
|
112
|
+
* again at the corrected instant and, if it changed, a second correction is
|
|
113
|
+
* computed using that re-read offset.
|
|
114
|
+
*
|
|
115
|
+
* The second correction is only trustworthy if it actually lands back on the
|
|
116
|
+
* target Y/M/D — re-reading the offset can itself land on the far side of
|
|
117
|
+
* *another* transition (this happens for zones that spring forward at or
|
|
118
|
+
* near midnight, e.g. America/Havana, America/Santiago, Atlantic/Azores: the
|
|
119
|
+
* re-read offset belongs to the transition that skipped local midnight
|
|
120
|
+
* entirely, and blindly applying it walks the candidate back onto the
|
|
121
|
+
* *previous* day instead of forward onto the first real instant of the
|
|
122
|
+
* target day). So the second correction is validated against the target
|
|
123
|
+
* Y/M/D before being trusted, falling back to the first correction — the
|
|
124
|
+
* earliest instant whose wall-clock date is on or after the target — when it
|
|
125
|
+
* isn't.
|
|
126
|
+
*/
|
|
127
|
+
function zonedStartOfDayMs(year, month, day, tz) {
|
|
128
|
+
const guess = Date.UTC(year, month - 1, day);
|
|
129
|
+
const offset = zonedOffsetMs(guess, tz);
|
|
130
|
+
const firstCorrection = guess - offset;
|
|
131
|
+
const offsetAtFirstCorrection = zonedOffsetMs(firstCorrection, tz);
|
|
132
|
+
if (offsetAtFirstCorrection === offset)
|
|
133
|
+
return firstCorrection;
|
|
134
|
+
const secondCorrection = guess - offsetAtFirstCorrection;
|
|
135
|
+
const secondCorrectionYmd = zonedYMD(secondCorrection, tz);
|
|
136
|
+
const secondCorrectionMatchesTarget = secondCorrectionYmd.year === year &&
|
|
137
|
+
secondCorrectionYmd.month === month &&
|
|
138
|
+
secondCorrectionYmd.day === day;
|
|
139
|
+
return secondCorrectionMatchesTarget ? secondCorrection : firstCorrection;
|
|
140
|
+
}
|
|
15
141
|
/**
|
|
16
142
|
* Epoch ms at local midnight of the day containing `refTs`.
|
|
17
143
|
* Defaults to `Date.now()` when `refTs` is omitted.
|
|
144
|
+
* Computed in the host's own local timezone unless `tz` (an IANA timezone
|
|
145
|
+
* name) is given, in which case midnight is computed in that zone instead.
|
|
18
146
|
*/
|
|
19
|
-
export function localStartOfDay(refTs) {
|
|
147
|
+
export function localStartOfDay(refTs, tz) {
|
|
148
|
+
if (tz) {
|
|
149
|
+
const ts = refTs == null ? Date.now() : refTs;
|
|
150
|
+
const { year, month, day } = zonedYMD(ts, tz);
|
|
151
|
+
return zonedStartOfDayMs(year, month, day, tz);
|
|
152
|
+
}
|
|
20
153
|
const d = refTs == null ? new Date() : new Date(refTs);
|
|
21
154
|
d.setHours(0, 0, 0, 0);
|
|
22
155
|
return d.getTime();
|
|
23
156
|
}
|
|
24
157
|
/**
|
|
25
|
-
* True iff `ts` and `refTs` (or now) fall on the same
|
|
158
|
+
* True iff `ts` and `refTs` (or now) fall on the same calendar day.
|
|
26
159
|
* Uses Y/M/D comparison so DST transitions don't introduce off-by-one bugs
|
|
27
160
|
* (a "day" can be 23 h or 25 h on DST boundaries; raw ts-range arithmetic
|
|
28
161
|
* gets that wrong, Y/M/D comparison doesn't).
|
|
162
|
+
* Compares Y/M/D in the host's own local timezone unless `tz` (an IANA
|
|
163
|
+
* timezone name) is given, in which case both `ts` and `refTs` are compared
|
|
164
|
+
* as observed in that same zone.
|
|
29
165
|
*/
|
|
30
|
-
export function isSameLocalDay(ts, refTs) {
|
|
166
|
+
export function isSameLocalDay(ts, refTs, tz) {
|
|
167
|
+
if (tz) {
|
|
168
|
+
const a = zonedYMD(ts, tz);
|
|
169
|
+
const b = zonedYMD(refTs == null ? Date.now() : refTs, tz);
|
|
170
|
+
return a.year === b.year && a.month === b.month && a.day === b.day;
|
|
171
|
+
}
|
|
31
172
|
const a = new Date(ts);
|
|
32
173
|
const b = refTs == null ? new Date() : new Date(refTs);
|
|
33
174
|
return (a.getFullYear() === b.getFullYear() &&
|
|
@@ -38,8 +179,14 @@ export function isSameLocalDay(ts, refTs) {
|
|
|
38
179
|
* Local-time YYYY-MM-DD key for `ts` (or now). Used as a Map key for per-day
|
|
39
180
|
* cost buckets. Must agree with localStartOfDay/isSameLocalDay so server-side
|
|
40
181
|
* bucketing and client-side filters draw the day boundary at the same instant.
|
|
182
|
+
* Computed in the host's own local timezone unless `tz` (an IANA timezone
|
|
183
|
+
* name) is given, in which case the key reflects Y/M/D in that zone instead.
|
|
41
184
|
*/
|
|
42
|
-
export function localDateKey(ts) {
|
|
185
|
+
export function localDateKey(ts, tz) {
|
|
186
|
+
if (tz) {
|
|
187
|
+
const { year, month, day } = zonedYMD(ts == null ? Date.now() : ts, tz);
|
|
188
|
+
return `${year}-${String(month).padStart(2, '0')}-${String(day).padStart(2, '0')}`;
|
|
189
|
+
}
|
|
43
190
|
const d = ts == null ? new Date() : new Date(ts);
|
|
44
191
|
const year = d.getFullYear();
|
|
45
192
|
const month = String(d.getMonth() + 1).padStart(2, '0');
|
package/dist/lib/date.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"date.js","sourceRoot":"","sources":["../../src/lib/date.ts"],"names":[],"mappings":"AAAA
|
|
1
|
+
{"version":3,"file":"date.js","sourceRoot":"","sources":["../../src/lib/date.ts"],"names":[],"mappings":"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"}
|